diff --git a/README.md b/README.md index f3ff527..a52f605 100644 --- a/README.md +++ b/README.md @@ -76,23 +76,78 @@ modifying the feed object that is passed to the create function. Note: It works for SSG and prerendered pages. ```ts +import type { H3Event } from "h3"; import type { NitroCtx, Feed } from "nuxt-module-feed"; +import { setHeader } from '#imports' +import process from 'node:process'; export default defineNitroPlugin((nitroApp) => { - nitroApp.hooks.hook("feed:generate", async ({ feed, options }: NitroCtx) => { + nitroApp.hooks.hook("feed:generate", async ({ feed, options }: NitroCtx, event: H3Event) => { switch (options.path) { case "/feed.xml": { - createTestFeed(feed); + createNuxtContentFeed(feed); break; } case "/feed2.xml": { createTestFeed(feed); break; } + + // { path: "/feed3.xml", type: "rss2", cacheTime: 60 * 15 } + case "/feed3.xml": { + setHeader(event, 'content-type', 'application/xml; charset=UTF-8'); + createNuxtContentFeed(feed); + break; + } + + // { path: "/feed3.atom", type: "atom1", cacheTime: 60 * 15 } + case "/feed3.atom": { + setHeader(event, 'content-type', 'application/atom+xml; charset=UTF-8'); + createNuxtContentFeed(feed); + break; + } + + // { path: "/feed3.json", type: "json1", cacheTime: 60 * 15 } + case "/feed3.json": { + setHeader(event, 'content-type', 'application/json; charset=UTF-8'); + createNuxtContentFeed(feed); + break; + } ... } }); + /** + * Nuxt Content + * https://content.nuxt.com/ + */ + function createNuxtContentFeed(feed: Feed, event: H3Event) { + feed.options = { + id: "Test Feed", + title: "Test Feed", + copyright: "Test company", + }; + feed.addCategory("Nuxt.js"); + feed.addContributor({ + name: "Miha Sedej", + email: "sedej.miha@gmail.com", + link: "https://tresko.dev/", + }); + + const posts = await queryCollection(event, 'posts').all() + const url = process.env.NUXT_SITE_URL || 'https://example.dev' + for (const post of posts) { + feed.addItem({ + id: post.id, + link: `${url}${post.path}`, + date: new Date(post.date), + title: post.title, + content: post.rawbody, + description: post.description, + }) + } + } + function createTestFeed(feed: Feed) { feed.options = { id: "Test Feed", diff --git a/playground/server/plugins/feed.ts b/playground/server/plugins/feed.ts index 2c3f788..d38deec 100644 --- a/playground/server/plugins/feed.ts +++ b/playground/server/plugins/feed.ts @@ -1,9 +1,11 @@ +import { H3Event } from 'h3'; import type { NitroCtx, Feed } from '../../../src/module' export default defineNitroPlugin((nitroApp) => { - nitroApp.hooks.hook('feed:generate', async ({ feed, options }: NitroCtx) => { + nitroApp.hooks.hook('feed:generate', async ({ feed, options }: NitroCtx, event: H3Event) => { switch(options.path) { case '/feed.xml': { + setHeader(event, 'content-type', 'application/xml; charset=UTF-8'); createTestFeed(feed) break } @@ -29,7 +31,7 @@ export default defineNitroPlugin((nitroApp) => { date: Date; image: string; }; - + const posts: Post[] = [ { title: "Post 1", @@ -71,6 +73,14 @@ export default defineNitroPlugin((nitroApp) => { date: new Date("2022-01-20"), image: "https://example.com/images/post5.jpg", }, + { + title: "帖子 6", + url: "https://example.com/post-6", + description: "这是第六篇帖子", + content: "除非有意外情况发生,否则那些故意造成伤害的人将被追究责任,他们的行为将被视为严重的过失。", + date: new Date("2025-01-30"), + image: "https://example.com/images/post5.jpg", + }, ]; posts.forEach(post => { @@ -92,4 +102,4 @@ export default defineNitroPlugin((nitroApp) => { link: 'https://tresko.dev/' }) } -}) \ No newline at end of file +}) diff --git a/src/runtime/server/feed.ts b/src/runtime/server/feed.ts index 9b6656b..ff61c36 100644 --- a/src/runtime/server/feed.ts +++ b/src/runtime/server/feed.ts @@ -16,14 +16,14 @@ function resolveContentType(type: FeedType) { return lookup[type] } -async function createFeed(options: SourceOptions): Promise { +async function createFeed(options: SourceOptions, event: H3Event): Promise { const feed = new Feed({ id: '', title: '', copyright: '', }) - await useNitroApp().hooks.callHook('feed:generate', { feed, options }) + await useNitroApp().hooks.callHook('feed:generate', { feed, options }, event) return feed[options.type]() } @@ -32,6 +32,6 @@ export default defineEventHandler(async (event: H3Event) => { const options = (feedOptions as Record)[event.node.req.url as string] setHeader(event, 'content-type', resolveContentType(options.type)) setHeader(event, 'cache-control', `max-age=${options.cacheTime}`) - const feed = await createFeed(options) + const feed = await createFeed(options, event) return feed -}) \ No newline at end of file +}) diff --git a/src/types.ts b/src/types.ts index c9ff25a..788020c 100644 --- a/src/types.ts +++ b/src/types.ts @@ -1,3 +1,5 @@ +import type { H3Event } from 'h3' + import type { Feed } from 'feed' export type { Feed } from 'feed' @@ -21,6 +23,6 @@ export interface NitroCtx { declare module 'nitropack' { interface NitroRuntimeHooks { - 'feed:generate': (ctx: NitroCtx) => void; + 'feed:generate': (ctx: NitroCtx, event: H3Event) => void; } -} \ No newline at end of file +}