feat: add RSS feed generation and update package metadata
- Implemented a new RSS feed generation feature in src/pages/feed.xml.ts, allowing users to follow blog updates. - Updated package.json and package-lock.json to include license information and new type definitions for markdown-it and sanitize-html. - Refactored createOgImage function to return Uint8Array instead of Buffer for better compatibility. - Simplified pageSchema by removing the optional mainEntityId parameter for cleaner schema generation.
This commit is contained in:
@@ -1,12 +1,13 @@
|
||||
import type { APIContext } from "astro";
|
||||
import { getCollection } from "astro:content";
|
||||
import MarkdownIt from "markdown-it";
|
||||
import rss from "@astrojs/rss";
|
||||
import sanitizeHtml from "sanitize-html";
|
||||
import { config } from "../config";
|
||||
|
||||
const parser = new MarkdownIt({ html: true, linkify: true });
|
||||
const parser = new MarkdownIt({ html: false, linkify: true });
|
||||
|
||||
export async function GET(context) {
|
||||
export async function GET(context: APIContext) {
|
||||
const title = "RSS Feed | Valentin Popov Blog";
|
||||
const description = "Follow the latest posts from Valentin Popov via RSS.";
|
||||
|
||||
@@ -17,13 +18,13 @@ export async function GET(context) {
|
||||
return rss({
|
||||
title,
|
||||
description,
|
||||
site: context.site,
|
||||
site: context.site ?? config.author.url,
|
||||
xmlns: {
|
||||
atom: "http://www.w3.org/2005/Atom",
|
||||
content: "http://purl.org/rss/1.0/modules/content/",
|
||||
dc: "http://purl.org/dc/elements/1.1/",
|
||||
},
|
||||
customData: [`<language>en</language>`, `<atom:link href="${feedUrl}" rel="self" type="application/rss+xml"/>`].join(""),
|
||||
customData: `<atom:link href="${feedUrl}" rel="self" type="application/rss+xml"/>`,
|
||||
items: posts.map((post) => ({
|
||||
title: post.data.title,
|
||||
description: post.data.description,
|
||||
@@ -36,8 +37,8 @@ export async function GET(context) {
|
||||
...sanitizeHtml.defaults.allowedAttributes,
|
||||
img: ["src", "alt", "title", "loading", "decoding"],
|
||||
code: ["class"],
|
||||
span: ["class", "style"],
|
||||
pre: ["class", "style"],
|
||||
span: ["class"],
|
||||
pre: ["class"],
|
||||
a: ["href", "name", "target", "rel"],
|
||||
},
|
||||
}),
|
||||
@@ -5,7 +5,7 @@ import { Resvg } from "@resvg/resvg-js";
|
||||
import dayjs from "dayjs";
|
||||
import satori from "satori";
|
||||
|
||||
export async function createOgImage(title: string, datePublished: Date): Promise<Buffer> {
|
||||
export async function createOgImage(title: string, datePublished: Date): Promise<Uint8Array> {
|
||||
const formattedDate = dayjs(datePublished).format("MMMM DD, YYYY");
|
||||
|
||||
const markup = await satori(
|
||||
|
||||
@@ -4,14 +4,13 @@ import { personId, websiteId } from "./ids";
|
||||
export type WebsiteSchemaParams = {
|
||||
readonly description: string;
|
||||
readonly lang: string;
|
||||
readonly mainEntityId?: string;
|
||||
readonly page: string;
|
||||
readonly siteUrl: string;
|
||||
readonly title: string;
|
||||
readonly type?: "WebPage" | "ProfilePage";
|
||||
};
|
||||
|
||||
export default ({ siteUrl, page, title, description, lang, type = "WebPage", mainEntityId }: WebsiteSchemaParams): WebPage | ProfilePage => {
|
||||
export default ({ siteUrl, page, title, description, lang, type = "WebPage" }: WebsiteSchemaParams): WebPage | ProfilePage => {
|
||||
const url = new URL(page, siteUrl).toString();
|
||||
|
||||
const base = {
|
||||
@@ -28,7 +27,7 @@ export default ({ siteUrl, page, title, description, lang, type = "WebPage", mai
|
||||
return {
|
||||
...base,
|
||||
"@type": "ProfilePage",
|
||||
"mainEntity": { "@id": mainEntityId ?? personId(siteUrl) },
|
||||
"mainEntity": { "@id": personId(siteUrl) },
|
||||
};
|
||||
}
|
||||
|
||||
|
||||
Reference in New Issue
Block a user