Update Astro v5.15.4
This commit is contained in:
@@ -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>
|
||||
|
||||
@@ -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;
|
||||
---
|
||||
|
||||
@@ -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 |
@@ -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
26
src/content.config.js
Normal 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 };
|
||||
|
||||
@@ -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,
|
||||
};
|
||||
@@ -29,15 +29,6 @@ Future expansion features under consideration include search function, OG valida
|
||||
|
||||

|
||||
|
||||
<video
|
||||
src="/videos/ricoog.mp4"
|
||||
controls
|
||||
width="100%"
|
||||
style="max-width:1280px;height:auto;"
|
||||
>
|
||||
Your browser does not support video playback.
|
||||
</video>
|
||||
|
||||
---
|
||||
|
||||
## 2. GradientsHub
|
||||
|
||||
@@ -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" />
|
||||
|
||||
@@ -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);
|
||||
---
|
||||
|
||||
@@ -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);
|
||||
---
|
||||
|
||||
|
||||
@@ -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">
|
||||
|
||||
@@ -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',
|
||||
};
|
||||
}),
|
||||
});
|
||||
}
|
||||
@@ -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
|
||||
|
||||
@@ -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>
|
||||
|
||||
Reference in New Issue
Block a user