From 5bf44577634935b9fa6d50b040abcd680035075f Mon Sep 17 00:00:00 2001 From: Kevin Zuniga Cuellar <46791833+kevinzunigacuellar@users.noreply.github.com> Date: Wed, 1 Nov 2023 14:41:53 -0700 Subject: [PATCH] feat: add support for adding sidebar badges to group headings (#995) Co-authored-by: HiDeoo <494699+HiDeoo@users.noreply.github.com> Co-authored-by: Chris Swithinbank <357379+delucis@users.noreply.github.com> --- .changeset/orange-pants-tell.md | 5 ++++ docs/src/components/sidebar-preview.astro | 1 + docs/src/content/docs/guides/sidebar.mdx | 26 ++++++++++++++++++- .../content/docs/reference/configuration.mdx | 2 +- .../basics/navigation-labels.test.ts | 1 + .../__tests__/basics/navigation-order.test.ts | 1 + .../__tests__/basics/navigation.test.ts | 1 + .../__tests__/i18n/navigation-order.test.ts | 4 +++ .../sidebar/navigation-attributes.test.ts | 6 +++++ .../sidebar/navigation-badges.test.ts | 6 +++++ .../sidebar/navigation-hidden.test.ts | 6 +++++ .../sidebar/navigation-order.test.ts | 6 +++++ .../__tests__/sidebar/navigation.test.ts | 6 +++++ .../__tests__/sidebar/vitest.config.ts | 1 + .../starlight/components/SidebarSublist.astro | 16 +++++++++--- packages/starlight/schemas/sidebar.ts | 4 +-- packages/starlight/utils/navigation.ts | 4 +++ 17 files changed, 89 insertions(+), 7 deletions(-) create mode 100644 .changeset/orange-pants-tell.md diff --git a/.changeset/orange-pants-tell.md b/.changeset/orange-pants-tell.md new file mode 100644 index 0000000000..a11ff966b7 --- /dev/null +++ b/.changeset/orange-pants-tell.md @@ -0,0 +1,5 @@ +--- +'@astrojs/starlight': minor +--- + +Adds support for adding sidebar badges to group headings diff --git a/docs/src/components/sidebar-preview.astro b/docs/src/components/sidebar-preview.astro index 732e766e08..bd10705d16 100644 --- a/docs/src/components/sidebar-preview.astro +++ b/docs/src/components/sidebar-preview.astro @@ -29,6 +29,7 @@ function makeEntries(items: SidebarConfig): SidebarEntry[] { label: item.label, entries: makeEntries(item.items as SidebarConfig), collapsed: item.collapsed, + badge: item.badge, }; }); } diff --git a/docs/src/content/docs/guides/sidebar.mdx b/docs/src/content/docs/guides/sidebar.mdx index 4370c9cc75..47d156df29 100644 --- a/docs/src/content/docs/guides/sidebar.mdx +++ b/docs/src/content/docs/guides/sidebar.mdx @@ -235,7 +235,7 @@ The `sidebar` frontmatter configuration is only used for autogenerated links and ## Badges -Links can also include a `badge` property to display a badge next to the link label. +Links, groups, and autogenerated groups can also include a `badge` property to display a badge next to their label. ```js starlight({ @@ -251,6 +251,12 @@ starlight({ }, ], }, + // An autogenerated group with a "Deprecated" badge. + { + label: 'Reference', + badge: 'Deprecated', + autogenerate: { directory: 'reference' }, + }, ], }); ``` @@ -269,6 +275,24 @@ The configuration above generates the following sidebar: }, ], }, + { + label: 'Reference', + badge: { text: 'Deprecated', variant: 'default'}, + items: [ + { + label: 'Configuration Reference', + link: '/reference/configuration/', + }, + { + label: 'Frontmatter Reference', + link: '/reference/frontmatter/', + }, + { + label: 'Overrides Reference', + link: '/reference/overrides/', + }, + ], + }, ]} /> diff --git a/docs/src/content/docs/reference/configuration.mdx b/docs/src/content/docs/reference/configuration.mdx index 19647ff8aa..8d1dfe6aca 100644 --- a/docs/src/content/docs/reference/configuration.mdx +++ b/docs/src/content/docs/reference/configuration.mdx @@ -183,10 +183,10 @@ sidebar: [ type SidebarItem = { label: string; translations?: Record; + badge?: string | BadgeConfig; } & ( | { link: string; - badge?: string | BadgeConfig; attrs?: Record; } | { items: SidebarItem[]; collapsed?: boolean } diff --git a/packages/starlight/__tests__/basics/navigation-labels.test.ts b/packages/starlight/__tests__/basics/navigation-labels.test.ts index 646253508c..a85b48cbed 100644 --- a/packages/starlight/__tests__/basics/navigation-labels.test.ts +++ b/packages/starlight/__tests__/basics/navigation-labels.test.ts @@ -36,6 +36,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/basics/navigation-order.test.ts b/packages/starlight/__tests__/basics/navigation-order.test.ts index 089ad8dbdb..6bcd2186f0 100644 --- a/packages/starlight/__tests__/basics/navigation-order.test.ts +++ b/packages/starlight/__tests__/basics/navigation-order.test.ts @@ -17,6 +17,7 @@ describe('getSidebar', () => { expect(getSidebar('/', undefined)).toMatchInlineSnapshot(` [ { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/basics/navigation.test.ts b/packages/starlight/__tests__/basics/navigation.test.ts index 7661132203..3d76a38efe 100644 --- a/packages/starlight/__tests__/basics/navigation.test.ts +++ b/packages/starlight/__tests__/basics/navigation.test.ts @@ -34,6 +34,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/i18n/navigation-order.test.ts b/packages/starlight/__tests__/i18n/navigation-order.test.ts index 95ecf27cf5..fb37ca62d4 100644 --- a/packages/starlight/__tests__/i18n/navigation-order.test.ts +++ b/packages/starlight/__tests__/i18n/navigation-order.test.ts @@ -46,6 +46,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -84,6 +85,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -99,6 +101,7 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -122,6 +125,7 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/sidebar/navigation-attributes.test.ts b/packages/starlight/__tests__/sidebar/navigation-attributes.test.ts index 7949fc67b9..66d3b0df45 100644 --- a/packages/starlight/__tests__/sidebar/navigation-attributes.test.ts +++ b/packages/starlight/__tests__/sidebar/navigation-attributes.test.ts @@ -32,6 +32,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -72,6 +73,10 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": { + "text": "Experimental", + "variant": "default", + }, "collapsed": false, "entries": [ { @@ -90,6 +95,7 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/sidebar/navigation-badges.test.ts b/packages/starlight/__tests__/sidebar/navigation-badges.test.ts index e6cf12dca3..542ab869db 100644 --- a/packages/starlight/__tests__/sidebar/navigation-badges.test.ts +++ b/packages/starlight/__tests__/sidebar/navigation-badges.test.ts @@ -39,6 +39,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -79,6 +80,10 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": { + "text": "Experimental", + "variant": "default", + }, "collapsed": false, "entries": [ { @@ -108,6 +113,7 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/sidebar/navigation-hidden.test.ts b/packages/starlight/__tests__/sidebar/navigation-hidden.test.ts index 5614d5857f..34c028a3e7 100644 --- a/packages/starlight/__tests__/sidebar/navigation-hidden.test.ts +++ b/packages/starlight/__tests__/sidebar/navigation-hidden.test.ts @@ -28,6 +28,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -68,6 +69,10 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": { + "text": "Experimental", + "variant": "default", + }, "collapsed": false, "entries": [ { @@ -83,6 +88,7 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/sidebar/navigation-order.test.ts b/packages/starlight/__tests__/sidebar/navigation-order.test.ts index 18896a1d12..0c17e5b1fd 100644 --- a/packages/starlight/__tests__/sidebar/navigation-order.test.ts +++ b/packages/starlight/__tests__/sidebar/navigation-order.test.ts @@ -28,6 +28,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -68,6 +69,10 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": { + "text": "Experimental", + "variant": "default", + }, "collapsed": false, "entries": [ { @@ -91,6 +96,7 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/sidebar/navigation.test.ts b/packages/starlight/__tests__/sidebar/navigation.test.ts index 2300c5c087..9255313eaa 100644 --- a/packages/starlight/__tests__/sidebar/navigation.test.ts +++ b/packages/starlight/__tests__/sidebar/navigation.test.ts @@ -28,6 +28,7 @@ describe('getSidebar', () => { "type": "link", }, { + "badge": undefined, "collapsed": false, "entries": [ { @@ -68,6 +69,10 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": { + "text": "Experimental", + "variant": "default", + }, "collapsed": false, "entries": [ { @@ -91,6 +96,7 @@ describe('getSidebar', () => { "type": "group", }, { + "badge": undefined, "collapsed": false, "entries": [ { diff --git a/packages/starlight/__tests__/sidebar/vitest.config.ts b/packages/starlight/__tests__/sidebar/vitest.config.ts index 56944082f0..a33f9541b7 100644 --- a/packages/starlight/__tests__/sidebar/vitest.config.ts +++ b/packages/starlight/__tests__/sidebar/vitest.config.ts @@ -28,6 +28,7 @@ export default defineVitestConfig({ // A group linking to all pages in the reference directory. { label: 'Reference', + badge: 'Experimental', autogenerate: { directory: 'reference' }, }, // A group linking to all pages in the api/v1 directory. diff --git a/packages/starlight/components/SidebarSublist.astro b/packages/starlight/components/SidebarSublist.astro index 393edf58f5..417e2dbf9f 100644 --- a/packages/starlight/components/SidebarSublist.astro +++ b/packages/starlight/components/SidebarSublist.astro @@ -36,7 +36,15 @@ interface Props { open={flattenSidebar(entry.entries).some((i) => i.isCurrent) || !entry.collapsed} > - {entry.label} +
+ {entry.label} + {entry.badge && ( + <> + {' '} + + + )} +
@@ -78,7 +86,8 @@ interface Props { display: flex; align-items: center; justify-content: space-between; - padding-inline: var(--sl-sidebar-item-padding-inline); + padding: 0.2em var(--sl-sidebar-item-padding-inline); + line-height: 1.4; cursor: pointer; user-select: none; } @@ -120,7 +129,8 @@ interface Props { background-color: var(--sl-color-text-accent); } - a > *:not(:last-child) { + a > *:not(:last-child), + .group-label > *:not(:last-child) { margin-inline-end: 0.25em; } diff --git a/packages/starlight/schemas/sidebar.ts b/packages/starlight/schemas/sidebar.ts index 4ee106eaf1..86eb7f87e4 100644 --- a/packages/starlight/schemas/sidebar.ts +++ b/packages/starlight/schemas/sidebar.ts @@ -9,6 +9,8 @@ const SidebarBaseSchema = z.object({ label: z.string(), /** Translations of the `label` for each supported language. */ translations: z.record(z.string()).default({}), + /** Adds a badge to the link item */ + badge: BadgeConfigSchema(), }); const SidebarGroupSchema = SidebarBaseSchema.extend({ @@ -29,8 +31,6 @@ export const SidebarLinkItemHTMLAttributesSchema = () => linkHTMLAttributesSchem const SidebarLinkItemSchema = SidebarBaseSchema.extend({ /** The link to this item’s content. Can be a relative link to local files or the full URL of an external page. */ link: z.string(), - /** Adds a badge to the link item */ - badge: BadgeConfigSchema(), /** HTML attributes to add to the link item. */ attrs: SidebarLinkItemHTMLAttributesSchema(), }); diff --git a/packages/starlight/utils/navigation.ts b/packages/starlight/utils/navigation.ts index c8a45b4ade..5710f55320 100644 --- a/packages/starlight/utils/navigation.ts +++ b/packages/starlight/utils/navigation.ts @@ -30,6 +30,7 @@ interface Group { label: string; entries: (Link | Group)[]; collapsed: boolean; + badge: Badge | undefined; } export type SidebarEntry = Link | Group; @@ -75,6 +76,7 @@ function configItemToEntry( label: pickLang(item.translations, localeToLang(locale)) || item.label, entries: item.items.map((i) => configItemToEntry(i, currentPathname, locale, routes)), collapsed: item.collapsed, + badge: item.badge, }; } } @@ -101,6 +103,7 @@ function groupFromAutogenerateConfig( label: pickLang(item.translations, localeToLang(locale)) || item.label, entries: sidebarFromDir(tree, currentPathname, locale, subgroupCollapsed ?? item.collapsed), collapsed: item.collapsed, + badge: item.badge, }; } @@ -231,6 +234,7 @@ function groupFromDir( label: dirName, entries, collapsed, + badge: undefined, }; }