mirror of
https://github.com/facebook/docusaurus.git
synced 2025-04-29 18:27:56 +02:00
feat(blog-plugin): limit option for blog feedOptions (#9189)
This commit is contained in:
parent
e0bb39a40a
commit
4ecc86f89f
8 changed files with 164 additions and 8 deletions
File diff suppressed because one or more lines are too long
|
@ -195,4 +195,47 @@ describe.each(['atom', 'rss', 'json'])('%s', (feedType) => {
|
|||
).toMatchSnapshot();
|
||||
fsMock.mockClear();
|
||||
});
|
||||
|
||||
it('filters to the first two entries using limit', async () => {
|
||||
const siteDir = path.join(__dirname, '__fixtures__', 'website');
|
||||
const outDir = path.join(siteDir, 'build-snap');
|
||||
const siteConfig = {
|
||||
title: 'Hello',
|
||||
baseUrl: '/myBaseUrl/',
|
||||
url: 'https://docusaurus.io',
|
||||
favicon: 'image/favicon.ico',
|
||||
};
|
||||
|
||||
// Build is quite difficult to mock, so we built the blog beforehand and
|
||||
// copied the output to the fixture...
|
||||
await testGenerateFeeds(
|
||||
{
|
||||
siteDir,
|
||||
siteConfig,
|
||||
i18n: DefaultI18N,
|
||||
outDir,
|
||||
} as LoadContext,
|
||||
{
|
||||
path: 'blog',
|
||||
routeBasePath: 'blog',
|
||||
tagsBasePath: 'tags',
|
||||
authorsMapPath: 'authors.yml',
|
||||
include: DEFAULT_OPTIONS.include,
|
||||
exclude: DEFAULT_OPTIONS.exclude,
|
||||
feedOptions: {
|
||||
type: [feedType],
|
||||
copyright: 'Copyright',
|
||||
limit: 2,
|
||||
},
|
||||
readingTime: ({content, defaultReadingTime}) =>
|
||||
defaultReadingTime({content}),
|
||||
truncateMarker: /<!--\s*truncate\s*-->/,
|
||||
} as PluginOptions,
|
||||
);
|
||||
|
||||
expect(
|
||||
fsMock.mock.calls.map((call) => call[1] as string),
|
||||
).toMatchSnapshot();
|
||||
fsMock.mockClear();
|
||||
});
|
||||
});
|
||||
|
|
|
@ -46,7 +46,7 @@ describe('validateOptions', () => {
|
|||
};
|
||||
expect(testValidate(userOptions)).toEqual({
|
||||
...userOptions,
|
||||
feedOptions: {type: ['rss'], title: 'myTitle', copyright: ''},
|
||||
feedOptions: {type: ['rss'], title: 'myTitle', copyright: '', limit: 20},
|
||||
});
|
||||
});
|
||||
|
||||
|
@ -58,7 +58,6 @@ describe('validateOptions', () => {
|
|||
beforeDefaultRehypePlugins: [markdownPluginsFunctionStub],
|
||||
remarkPlugins: [[markdownPluginsFunctionStub, {option1: '42'}]],
|
||||
rehypePlugins: [
|
||||
// @ts-expect-error: it seems to work in practice
|
||||
markdownPluginsObjectStub,
|
||||
[markdownPluginsFunctionStub, {option1: '42'}],
|
||||
],
|
||||
|
@ -95,7 +94,7 @@ describe('validateOptions', () => {
|
|||
}),
|
||||
).toEqual({
|
||||
...defaultOptions,
|
||||
feedOptions: {type: ['rss', 'atom', 'json'], copyright: ''},
|
||||
feedOptions: {type: ['rss', 'atom', 'json'], copyright: '', limit: 20},
|
||||
});
|
||||
});
|
||||
|
||||
|
@ -106,7 +105,7 @@ describe('validateOptions', () => {
|
|||
}),
|
||||
).toEqual({
|
||||
...defaultOptions,
|
||||
feedOptions: {type: null},
|
||||
feedOptions: {type: null, limit: 20},
|
||||
});
|
||||
});
|
||||
|
||||
|
@ -125,7 +124,12 @@ describe('validateOptions', () => {
|
|||
}),
|
||||
).toEqual({
|
||||
...defaultOptions,
|
||||
feedOptions: {type: ['rss', 'atom'], title: 'title', copyright: ''},
|
||||
feedOptions: {
|
||||
type: ['rss', 'atom'],
|
||||
title: 'title',
|
||||
copyright: '',
|
||||
limit: 20,
|
||||
},
|
||||
});
|
||||
});
|
||||
|
||||
|
|
|
@ -42,7 +42,12 @@ async function generateBlogFeed({
|
|||
const {url: siteUrl, baseUrl, title, favicon} = siteConfig;
|
||||
const blogBaseUrl = normalizeUrl([siteUrl, baseUrl, routeBasePath]);
|
||||
|
||||
const updated = blogPosts[0]?.metadata.date;
|
||||
const blogPostsForFeed =
|
||||
feedOptions.limit === false || feedOptions.limit === null
|
||||
? blogPosts
|
||||
: blogPosts.slice(0, feedOptions.limit);
|
||||
|
||||
const updated = blogPostsForFeed[0]?.metadata.date;
|
||||
|
||||
const feed = new Feed({
|
||||
id: blogBaseUrl,
|
||||
|
@ -59,7 +64,7 @@ async function generateBlogFeed({
|
|||
options.feedOptions.createFeedItems ?? defaultCreateFeedItems;
|
||||
|
||||
const feedItems = await createFeedItems({
|
||||
blogPosts,
|
||||
blogPosts: blogPostsForFeed,
|
||||
siteConfig,
|
||||
outDir,
|
||||
defaultCreateFeedItems,
|
||||
|
|
|
@ -22,7 +22,7 @@ import type {
|
|||
import type {OptionValidationContext} from '@docusaurus/types';
|
||||
|
||||
export const DEFAULT_OPTIONS: PluginOptions = {
|
||||
feedOptions: {type: ['rss', 'atom'], copyright: ''},
|
||||
feedOptions: {type: ['rss', 'atom'], copyright: '', limit: 20},
|
||||
beforeDefaultRehypePlugins: [],
|
||||
beforeDefaultRemarkPlugins: [],
|
||||
admonitions: true,
|
||||
|
@ -123,6 +123,9 @@ const PluginOptionSchema = Joi.object<PluginOptions>({
|
|||
}),
|
||||
language: Joi.string(),
|
||||
createFeedItems: Joi.function(),
|
||||
limit: Joi.alternatives()
|
||||
.try(Joi.number(), Joi.valid(null), Joi.valid(false))
|
||||
.default(DEFAULT_OPTIONS.feedOptions.limit),
|
||||
}).default(DEFAULT_OPTIONS.feedOptions),
|
||||
authorsMapPath: Joi.string().default(DEFAULT_OPTIONS.authorsMapPath),
|
||||
readingTime: Joi.function().default(() => DEFAULT_OPTIONS.readingTime),
|
||||
|
|
|
@ -272,6 +272,8 @@ yarn workspace v1.22.19image` is a collocated image path, this entry will be the
|
|||
language?: string;
|
||||
/** Allow control over the construction of BlogFeedItems */
|
||||
createFeedItems?: CreateFeedItemsFn;
|
||||
/** Limits the feed to the specified number of posts, false|null for all */
|
||||
limit?: number | false | null;
|
||||
};
|
||||
|
||||
type DefaultCreateFeedItemsParams = {
|
||||
|
|
|
@ -68,6 +68,7 @@ Accepted fields:
|
|||
| `feedOptions` | _See below_ | `{type: ['rss', 'atom']}` | Blog feed. |
|
||||
| `feedOptions.type` | <code><a href="#FeedType">FeedType</a> \| <a href="#FeedType">FeedType</a>[] \| 'all' \| null</code> | **Required** | Type of feed to be generated. Use `null` to disable generation. |
|
||||
| `feedOptions.createFeedItems` | <code><a href="#CreateFeedItemsFn">CreateFeedItemsFn</a> \| undefined</code> | `undefined` | An optional function which can be used to transform and / or filter the items in the feed. |
|
||||
| `feedOptions.limit` | `number \| null \| false` | `20` | Limits the feed to the specified number of posts, `false` or `null` for all entries. Defaults to `20`. |
|
||||
| `feedOptions.title` | `string` | `siteConfig.title` | Title of the feed. |
|
||||
| `feedOptions.description` | `string` | <code>\`$\{siteConfig.title} Blog\`</code> | Description of the feed. |
|
||||
| `feedOptions.copyright` | `string` | `undefined` | Copyright message. |
|
||||
|
|
|
@ -520,6 +520,7 @@ type BlogOptions = {
|
|||
description?: string;
|
||||
copyright: string;
|
||||
language?: string; // possible values: http://www.w3.org/TR/REC-html40/struct/dirlang.html#langcodes
|
||||
limit?: number | false | null; // defaults to 20
|
||||
/** Allow control over the construction of BlogFeedItems */
|
||||
createFeedItems?: (params: {
|
||||
blogPosts: BlogPost[];
|
||||
|
|
Loading…
Add table
Reference in a new issue