Update Astro v5.15.4

This commit is contained in:
ricocc
2025-11-08 16:20:26 +08:00
parent f1bcb1489f
commit 4cf082c589
22 changed files with 181 additions and 236 deletions

View File

@@ -5,7 +5,7 @@ const { title, description } = Astro.props;
<div class="relative z-20 w-full mx-auto mt-12 mb-16 text-center">
<h2
class="text-3xl font-brand text-center tracking-normal text-neutral-800 dark:text-neutral-100 sm:text-4xl lg:text-5xl"
class="text-4xl font-brand text-center tracking-normal sm:text-5xl"
>
<AnimatedText delay={0.2} stagger={0.08} content={title} />
</h2>

View File

@@ -49,20 +49,25 @@ if (pagination.enable) {
}
// 为每篇文章添加链接属性 - 创建新对象而不是修改原对象
const postsWithLinks = posts.map(post => ({
...post,
data: {
...post.data,
link: `/blog/${post.slug}`
}
}));
const postsWithLinks = posts.map(post => {
// 根据 Astro v5 官方文档entry.id 就是条目的唯一标识符
// 直接使用 entry.id 生成 URL对于 [...slug] 路由id 已经是正确的路径
const link = `/blog/${post.id}`;
return {
...post,
data: {
...post.data,
link
}
};
});
// 为特色文章创建带链接的版本
const featuredPostWithLink = featuredPost ? {
...featuredPost,
data: {
...featuredPost.data,
link: `/blog/${featuredPost.slug}`
link: `/blog/${featuredPost.id}`
}
} : null;
---

View File

@@ -1,22 +1,2 @@
<!-- <svg width="1920" height="717" viewBox="0 0 1920 717" fill="none" xmlns="http://www.w3.org/2000/svg" class="absolute top-0 left-0 right-0 w-full z-0 h-auto lg:top-[-20%] event-none">
<g clip-path="url(#clip0_619_11042)">
<g opacity="0.24" filter="url(#filter0_f_619_11042)">
<ellipse cx="1000" cy="241" rx="1000" ry="241" transform="matrix(1 0 0 -1 0 331)" fill="#4A3AFF"/>
</g>
</g>
<defs>
<filter id="filter0_f_619_11042" x="-320" y="-471" width="2640" height="1122" filterUnits="userSpaceOnUse" color-interpolation-filters="sRGB">
<feFlood flood-opacity="0" result="BackgroundImageFix"/>
<feBlend mode="normal" in="SourceGraphic" in2="BackgroundImageFix" result="shape"/>
<feGaussianBlur stdDeviation="160" result="effect1_foregroundBlur_619_11042"/>
</filter>
<clipPath id="clip0_619_11042">
<rect width="2000" height="868" fill="white" transform="translate(0 -151)"/>
</clipPath>
</defs>
</svg> -->
<svg aria-hidden="true" class="pointer-events-none absolute top-[-20%] inset-0 [z-index:-1] size-full h-[50%] fill-blue-500/50 stroke-blue-500/50 [mask-image:linear-gradient(to_bottom,_#ffffffad,_transparent)] z-2 opacity-[.30]"><defs><pattern id=":S1:" width="12" height="12" patternUnits="userSpaceOnUse" x="-1" y="-1"><path d="M.5 12V.5H12" fill="none" stroke-dasharray="0"></path></pattern></defs><rect width="100%" height="100%" stroke-width="0" fill="url(#:S1:)"></rect></svg>

Before

Width:  |  Height:  |  Size: 1.4 KiB

After

Width:  |  Height:  |  Size: 486 B

View File

@@ -1,6 +1,6 @@
// Get site URL from environment variable, use default value if not set
// Note: Please set the correct PUBLIC_SITE_URL in .env file after first deployment
const SITE_URL = process.env.PUBLIC_SITE_URL || 'https://portfolio.ricoui.com/';
const SITE_URL = import.meta.env.PUBLIC_SITE_URL || 'https://portfolio.ricoui.com/';
export const siteConfig = {
title: "Ricoui Portfolio",

26
src/content.config.js Normal file
View File

@@ -0,0 +1,26 @@
// 1. 从 `astro:content` 导入工具函数
import { defineCollection, z } from 'astro:content';
// 2. 导入加载器
import { glob } from 'astro/loaders';
// 3. 定义你的集合
const post = defineCollection({
// 使用 glob 加载器从 src/content/post 目录加载所有 .mdx 文件
loader: glob({ pattern: '**/*.{md,mdx}', base: './src/content/post' }),
// Type-check frontmatter using a schema
schema: z.object({
title: z.string(),
description: z.string(),
publishDate: z.coerce.date(),
read: z.number().optional(),
tags: z.array(z.string()).optional(),
img: z.string().optional(),
img_alt: z.string().optional(),
featured: z.boolean().optional(),
}),
});
// 4. 导出一个 `collections` 对象来注册你的集合
export const collections = { post };

View File

@@ -1,18 +0,0 @@
import { defineCollection, z } from "astro:content";
const postCollection = defineCollection({
schema: z.object({
title: z.string(),
description: z.string(),
publishDate: z.coerce.date(),
read: z.number().optional(),
tags: z.array(z.string()).optional(),
img: z.string().optional(),
img_alt: z.string().optional(),
featured: z.boolean().optional(),
}),
});
export const collections = {
post: postCollection,
};

View File

@@ -29,15 +29,6 @@ Future expansion features under consideration include search function, OG valida
![001-ricoog](001-ricoog.jpg)
<video
src="/videos/ricoog.mp4"
controls
width="100%"
style="max-width:1280px;height:auto;"
>
Your browser does not support video playback.
</video>
---
## 2. GradientsHub

View File

@@ -26,8 +26,7 @@ const {
<title>{title}</title>
<meta name="description" content={description} />
<meta name="keywords" content={keywords} />
<meta name="author" content="ricoui.com" />
<meta name="generator" content={Astro.generator} />
<meta name="author" content={siteConfig.author} />
<!-- Open Graph Tags -->
<meta property="og:type" content="website" />

View File

@@ -1,18 +1,39 @@
---
import { getCollection } from "astro:content";
import { getCollection, render } from "astro:content";
import PostLayout from "@/layouts/PostLayout.astro";
import Toc from '@/components/widgets/Toc.astro';
// 根据 Astro v5/v6对于 SSG 模式下的动态路由,需要使用 getStaticPaths()
// 来告诉 Astro 在构建时生成哪些页面
export async function getStaticPaths() {
const postEntries = await getCollection("post");
return postEntries.map((entry) => ({
params: { slug: entry.slug },
props: { entry },
}));
return postEntries.map((entry) => {
// 根据 Astro v5 官方文档entry.id 就是条目的唯一标识符
// 对于 [...slug] 路由,需要将 entry.id 转换为 slug 数组
// entry.id 已经是相对于集合根目录的路径,例如 "dir/index" 或 "dir"
// 注意:对于 [...slug] 路由params.slug 应该是字符串Astro 会自动处理
const slugString = entry.id;
return {
params: { slug: slugString },
props: { entry },
};
});
}
// 使用 [...slug] 路由来处理包含斜杠的路径(官方推荐)
// slug 参数是数组格式,需要转换为字符串来匹配 entry.id
const { slug } = Astro.params;
const slugString = Array.isArray(slug) ? slug.join('/') : (slug || '');
// 从 props 获取 entry在 SSG 模式下通过 getStaticPaths 传递)
const { entry } = Astro.props;
const { Content, headings } = await entry.render();
// 如果找不到文章,返回 404
if (!entry) {
return Astro.redirect("/404");
}
const { Content, headings } = await render(entry);
const filtered = headings.filter(h => h.depth <= 2);
---

View File

@@ -7,7 +7,9 @@ import { getCollection } from "astro:content";
// 定义每页显示的文章数量
export const POSTS_PER_PAGE = 6;
// 生成分页路径
// 根据 Astro v5/v6对于 SSG 模式下的分页路由,仍然需要使用 getStaticPaths()
// 这是因为需要告诉 Astro 在构建时生成哪些页面
// 注意params 必须是字符串类型(符合 v6 要求)
export async function getStaticPaths() {
const allPosts = await getCollection("post");
@@ -25,21 +27,18 @@ export async function getStaticPaths() {
// 使用移除特色文章后的文章数量计算总页数
const totalPages = Math.ceil(posts.length / POSTS_PER_PAGE);
// 返回所有分页路径,确保 params.page 是字符串类型v6 要求)
return Array.from({ length: totalPages }, (_, i) => {
const page = i + 1;
return {
params: { page: page.toString() },
props: { page }
props: { page: page.toString() }
};
});
}
// 添加类型注解
interface Props {
page: string;
}
const { page }: Props = Astro.props;
// 从 props 获取页码(在 SSG 模式下通过 getStaticPaths 传递)
const { page } = Astro.props;
const currentPage = parseInt(page);
---

View File

@@ -16,7 +16,7 @@ description="Welcome to Rico's portfolio site! Explore my work as a web/UI desig
keywords="Rico, Portfolio, Web Design, UI Design, Frontend Development, Creative Designer"
>
<div
class="relative site-container z-20 w-full mx-auto mt-16 px-7 md:mt-18 lg:mt-20 xl:px-0"
class="relative site-container z-20 w-full mx-auto mt-16 px-4 md:mt-18 lg:mt-20 xl:px-0"
>
<div class="relative w-full px-4 flex flex-col items-center justify-between md:flex-row mb-16 ">
<div class="relative w-full md:max-w-[420px] md:w-1/2 text-center sm:text-left sm:-mt-8">

View File

@@ -7,13 +7,15 @@ export async function GET(context) {
title: 'Rico Portfolio Template Astro',
description: 'Astro Blog Template by Rico UI',
site: context.site,
items: blog.map((post) => ({
title: post.data.title,
pubDate: post.data.pubDate,
description: post.data.description,
// ...post.data,
link: `/blog/${post.slug}/`,
stylesheet: '/rss/pretty-feed-v3.xsl',
})),
items: blog.map((post) => {
const link = `/blog/${post.id}/`;
return {
title: post.data.title,
pubDate: post.data.publishDate,
description: post.data.description,
link,
stylesheet: '/rss/pretty-feed-v3.xsl',
};
}),
});
}

View File

@@ -6,7 +6,8 @@ import ActionBar from "@/components/widgets/ActionBar.astro";
import SeparatorLine from "@/components/elements/SeparatorLine.astro";
//自动导入 Image 组件和图像
const allImages = await Astro.glob('../../assets/work/luonmodels/*.{jpg,png,webp}');
const allImagesModules = import.meta.glob('../../assets/work/luonmodels/*.{jpg,png,webp}', { eager: true });
const allImages = Object.values(allImagesModules) as Array<{ default: any }>;
const logoUrl = "https://luonmodels.vercel.app/favicon.png";
---
<PostLayout

View File

@@ -5,8 +5,6 @@ import PageHeader from "@/components/elements/PageHeader.astro";
import ActionBar from "@/components/widgets/ActionBar.astro";
import SeparatorLine from "@/components/elements/SeparatorLine.astro";
//自动导入 Image 组件和图像
// const allImages = await Astro.glob('../../assets/work/ricoblog2024/*.{jpg,png,webp}');
// 手动导入图片
import P_01 from "../../assets/work/ricoblog2024/P_01.jpg";
@@ -29,7 +27,7 @@ import logoUrl from "../../assets/work/ricoblog2024/logo.png";
<main class="work-wrapper">
<PageHeader
title="Rico Designer Blog 2024"
tags={["Designer","Portfolio","Open Source"]}
tags={["Designer","Portfolio","Open Source"]}
className="mb-6 md:mb-8"
>
</PageHeader>
@@ -52,11 +50,7 @@ import logoUrl from "../../assets/work/ricoblog2024/logo.png";
<Image src={img} alt={`Rico Blog 2024 设计图 ${index + 1}`} class="w-full h-full object-cover" loading="lazy" decoding="async" quality={100}/>
</picture>
))}
<!-- {images.map((img, index) => (
<picture class="picture mt-8 md:mt-12 mb-8 md:mb-12 rounded-2xl overflow-hidden">
<Image src={img.default} alt={`Image ${index + 1}`} class="w-full h-full object-cover" loading="lazy" decoding="async" quality={100}/>
</picture>
))} -->
</div>
</section>
</main>