mirror of
https://github.com/reonokiy/blog.nokiy.net.git
synced 2025-06-16 11:41:17 +02:00
feat: automatically generate Open Graph cards
This commit is contained in:
parent
9b9bdb2811
commit
a556a622ab
14 changed files with 59 additions and 30 deletions
|
@ -14,8 +14,8 @@ export const themeConfig: ThemeConfig = {
|
|||
// site url
|
||||
url: 'https://retypeset.radishzz.cc',
|
||||
// favicon url
|
||||
// support only webp, svg or png
|
||||
favicon: '/image/Logo.svg', // https://example.com/logo.svg
|
||||
// support only ico or png for best compatibility with Open Graph and RSS avatar
|
||||
favicon: '/image/Astro-Icon.png', // https://example.com/logo.png
|
||||
},
|
||||
// SITE INFORMATION >>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>>> END
|
||||
|
||||
|
|
|
@ -7,4 +7,4 @@ pin: 99
|
|||
lang: en
|
||||
---
|
||||
|
||||
Retypeset is a static blog theme based on the <a href="https://astro.build/">Astro</a> framework, inspired by <a href="https://astro-theme-typography.vercel.app/">Typography</a>. Retypeset establishes a new visual standard and reimagines the layout of all pages, offering a reading experience similar to paper books, reviving the beauty of typography. Details in every sight, elegance in every space.
|
||||
Retypeset is a static blog theme based on the [Astro](https://astro.build/) framework, inspired by [Typography](https://astro-theme-typography.vercel.app/). Retypeset establishes a new visual standard and reimagines the layout of all pages, offering a reading experience similar to paper books, reviving the beauty of typography. Details in every sight, elegance in every space.
|
||||
|
|
|
@ -7,4 +7,4 @@ pin: 99
|
|||
lang: zh
|
||||
---
|
||||
|
||||
Retypeset 是一款基于<a href="https://astro.build/">Astro</a>框架的静态博客主题,设计灵感来自<a href="https://astro-theme-typography.vercel.app/">Typography</a>。本主题通过建立全新的视觉规范,对所有页面进行重新编排,打造纸质书页般的阅读体验,再现版式之美。所见皆为细节,方寸尽显优雅。
|
||||
Retypeset 是一款基于[Astro](https://astro.build/)框架的静态博客主题,设计灵感来自[Typography](https://astro-theme-typography.vercel.app/)。本主题通过建立全新的视觉规范,对所有页面进行重新编排,打造纸质书页般的阅读体验,再现版式之美。所见皆为细节,方寸尽显优雅。
|
||||
|
|
|
@ -13,23 +13,23 @@ const { postTitle, postDescription, postSlug } = Astro.props
|
|||
const { title, subtitle, description, author, url, favicon } = themeConfig.site
|
||||
const { mode, light: { background: lightMode }, dark: { background: darkMode } } = themeConfig.color
|
||||
const { locale, moreLocale } = themeConfig.global
|
||||
// TODO: Change openGraph image fallback url
|
||||
const { verification = {}, twitterID = '', googleAnalyticsID = '', umamiAnalyticsID = '', openGraph = 'https://placehold.co/1200x630' } = themeConfig.seo ?? {}
|
||||
const { verification = {}, twitterID = '', googleAnalyticsID = '', umamiAnalyticsID = '', openGraph: ogUrl } = themeConfig.seo ?? {}
|
||||
const { google = '', bing = '', yandex = '', baidu = '' } = verification
|
||||
const { commentURL = '', imageHostURL = '', customGoogleAnalyticsJS = '', customUmamiAnalyticsJS = '' } = themeConfig.preload
|
||||
|
||||
const initMetaTheme = mode === 'dark' ? darkMode : lightMode
|
||||
const pageTitle = postTitle ? `${postTitle} | ${title}` : `${title} - ${subtitle}`
|
||||
const pageDescription = postDescription || description
|
||||
const pageImage = postSlug ? `${url}/og/${postSlug}.png` : `${openGraph}`
|
||||
// TODO: Change openGraph image fallback url
|
||||
const openGraph = typeof ogUrl === 'string' ? ogUrl : 'https://placehold.co/1200x630'
|
||||
const pageImage = postSlug ? `${url}/og/${postSlug}.png` : openGraph
|
||||
---
|
||||
<head>
|
||||
<!-- Basic info -->
|
||||
<meta charset="utf-8" />
|
||||
<meta name="viewport" content="width=device-width, initial-scale=1, viewport-fit=cover" />
|
||||
{favicon.toLowerCase().endsWith('.webp') && <link rel="icon" type="image/webp" href={favicon} />}
|
||||
{favicon.toLowerCase().endsWith('.svg') && <link rel="icon" type="image/svg+xml" href={favicon} />}
|
||||
{favicon.toLowerCase().endsWith('.png') && <link rel="icon" type="image/png" href={favicon} />}
|
||||
{favicon.toLowerCase().endsWith('.ico') && <link rel="icon" type="image/x-icon" href={favicon} />}
|
||||
<title>{pageTitle}</title>
|
||||
<meta name="description" content={pageDescription} />
|
||||
<meta name="author" content={author} />
|
||||
|
@ -65,7 +65,7 @@ const pageImage = postSlug ? `${url}/og/${postSlug}.png` : `${openGraph}`
|
|||
<meta property="og:site_name" content={title} />
|
||||
|
||||
<!-- Twitter Card -->
|
||||
<meta name="twitter:card" content="summary" />
|
||||
<meta name="twitter:card" content="summary_large_image" />
|
||||
<meta name="twitter:title" content={pageTitle} />
|
||||
<meta name="twitter:description" content={pageDescription} />
|
||||
<meta name="twitter:image" content={pageImage} />
|
||||
|
|
|
@ -2,6 +2,7 @@
|
|||
import Waline from '@/components/Comments/Waline.astro'
|
||||
import Layout from '@/layouts/Layout.astro'
|
||||
import { checkSlugDuplication } from '@/utils/content'
|
||||
import { generateDescription } from '@/utils/description'
|
||||
import { generateMultiLangPostPaths } from '@/utils/i18n/route'
|
||||
import { getCollection } from 'astro:content'
|
||||
|
||||
|
@ -17,10 +18,15 @@ export async function getStaticPaths() {
|
|||
}
|
||||
|
||||
const { post } = Astro.props
|
||||
const description = generateDescription(post)
|
||||
const { Content, remarkPluginFrontmatter } = await post.render()
|
||||
---
|
||||
|
||||
<Layout>
|
||||
<Layout
|
||||
postTitle={post.data.title}
|
||||
postDescription={description}
|
||||
postSlug={post.slug}
|
||||
>
|
||||
<article>
|
||||
<h1>{post.data.title}</h1>
|
||||
<time>
|
||||
|
|
|
@ -1,16 +1,23 @@
|
|||
import { themeConfig } from '@/config'
|
||||
import { generateDescription } from '@/utils/description'
|
||||
import { OGImageRoute } from 'astro-og-canvas'
|
||||
import { getCollection } from 'astro:content'
|
||||
|
||||
// eslint-disable-next-line antfu/no-top-level-await
|
||||
const blogEntries = await getCollection('posts')
|
||||
|
||||
// 确定favicon路径是完整URL还是相对路径
|
||||
const logoPath = themeConfig.site.favicon.startsWith('http')
|
||||
? themeConfig.site.favicon
|
||||
: `./public${themeConfig.site.favicon}`
|
||||
|
||||
// Convert to page data objects
|
||||
const pages = Object.fromEntries(
|
||||
blogEntries.map(({ slug, data }) => [
|
||||
slug,
|
||||
blogEntries.map(post => [
|
||||
post.slug,
|
||||
{
|
||||
title: data.title,
|
||||
description: data.description || '',
|
||||
title: post.data.title,
|
||||
description: post.data.description || generateDescription(post),
|
||||
},
|
||||
]),
|
||||
)
|
||||
|
@ -22,7 +29,27 @@ export const { getStaticPaths, GET } = OGImageRoute({
|
|||
getImageOptions: (_path, page) => ({
|
||||
title: page.title,
|
||||
description: page.description,
|
||||
border: { width: 10 },
|
||||
padding: 40,
|
||||
logo: {
|
||||
path: logoPath,
|
||||
size: [80],
|
||||
},
|
||||
font: {
|
||||
title: {
|
||||
families: ['Noto Sans SC'],
|
||||
weight: 'Bold',
|
||||
color: [34, 33, 36],
|
||||
lineHeight: 1.5,
|
||||
},
|
||||
description: {
|
||||
families: ['Noto Sans SC'],
|
||||
color: [72, 71, 74],
|
||||
lineHeight: 1.5,
|
||||
},
|
||||
},
|
||||
fonts: [
|
||||
'https://raw.githubusercontent.com/notofonts/noto-cjk/main/Sans/SubsetOTF/SC/NotoSansSC-Bold.otf',
|
||||
'https://raw.githubusercontent.com/notofonts/noto-cjk/main/Sans/SubsetOTF/SC/NotoSansSC-Regular.otf',
|
||||
],
|
||||
bgGradient: [[242, 241, 245]],
|
||||
}),
|
||||
})
|
||||
|
|
|
@ -5,7 +5,7 @@ import sanitizeHtml from 'sanitize-html'
|
|||
const parser = new MarkdownIt()
|
||||
|
||||
// Generate an excerpt from Markdown content
|
||||
export function generateExcerpt(content: string, length: number = 100): string {
|
||||
export function generateExcerpt(content: string, length: number = 98): string {
|
||||
if (!content)
|
||||
return ''
|
||||
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue