Skip to content

Limiting number of versions visible in the version dropdown switch #10833

Closed
@hrumhurum

Description

Have you read the Contributing Guidelines on issues?

Description

The proposed feature allows to declutter the UI/UX by limiting the maximum number of versions that are shown in the version dropdown.

Has this been requested on Canny?

No response

Motivation

When documentation has multiple versions, Docusaurus shows a helpful dropdown switch populated with them. Unfortunately, the switch becomes visually overcrowded relatively quickly by trying to offer too many versions at the same time:

{354351EC-E1C0-432F-A796-B00CC5ACE351}

While it depends on a product the documentation is offered for, users tend to stick to more recent versions with a greater probability. We can utilize this observation to offer a better UX for the version selection.

For example, the product I work on has a quite a few versions, and visitors are going to have troubles selecting a version with the existing version switcher UX due to visual clutter. At the same time, we cannot really delete older versions because they serve a considerable minority of customers who prefer to stick to older product versions for X reasons. (Especially given the fact that the product offers online-only help as an installation option, it is important to preserve its online presence, mostly for service continuity reasons.)

By limiting the number of versions shown in the dropdown switcher, we declutter the UX. To cover even older versions, we (optionally) add "All versions" dropdown item that leads to a custom /versions page that offers the full list of versions in a categorized manner. The standalone /versions page is created and maintained manually, as well as an optional "All versions" dropdown item.

API design

To limit the maximum number of versions that are shown in the version switch UI control, a Docusaurus user defines optional dropdownMaxItemCount property for the docsVersionDropdown navigation bar item in the theme configuration section of docusaurus.config.ts file:

const config: Config = {
  // ...
  themeConfig: {
    // ...
    navbar: {
      items: [
        // ...
        {
          type: "docsVersionDropdown",
          position: "right",
          dropdownActiveClassDisabled: true,
+         dropdownMaxItemCount: 4,
          dropdownItemsAfter: [
            {
              to: "/versions",
              label: "All versions"
            },
          ]
        },
      ]
    }
  },
  // ...
};

Additionally, a Docusaurus user may add a custom mechanism for accessing older versions. For example, it can be a custom page "All versions" which is defined in dropdownItemsAfter property in the sample above.

The effect of the proposed options is that the maximum number of the displayed dropdown versions is now limited to the specified value (4):

{93CEC435-A603-4430-9042-98A4AD3AF7C7}

Have you tried building it?

As a proof of concept, I have implemented the proposed feature. It required changes to @docusaurus/theme-classic and @docusaurus/plugin-content-docs packages.

Live preview

  1. The website with the proposed feature on (no UX problems)
  2. The original website without the proposed feature (it has UX problems due to the constantly growing number of versions)

Implementation stages

Stage 1 of 2. Limiting the number of displayed versions in the dropdown

This is a simple change that required changes in @docusaurus/theme-classic/src/theme/NavbarItem/DocsVersionDropdownNavbarItem.tsx component. The core algorithm perfrorms a slice of the version array according to the specified dropdownMaxItemCount value:

  const items = [
    ...dropdownItemsBefore,
-   ...versions.map(versionToLink),
+   ...versions.slice(0, dropdownMaxItemCount).map(versionToLink),
    ...dropdownItemsAfter,
  ];

The dropdownMaxItemCount option has formal constraints:

const DocsVersionDropdownNavbarItemSchema = NavbarItemBaseSchema.append({
  type: Joi.string().equal('docsVersionDropdown').required(),
  docsPluginId: Joi.string(),
  dropdownActiveClassDisabled: Joi.boolean(),
+ dropdownMaxItemCount: Joi.number().integer().min(0),
  dropdownItemsBefore: Joi.array().items(DropdownSubitemSchema).default([]),
  dropdownItemsAfter: Joi.array().items(DropdownSubitemSchema).default([]),
});

Notably, the dropdownMaxItemCount option explicitly allows 0 value, giving a space for further UI customizations.

Stage 2 of 2. Storage persistence of a selected version

The existing docsVersionDropdown component exhibits an interesting behavior of storing a selected version in a persistent storage (localStorage). This is required in order to ensure that an end-user always navigates in the scope of a selected version, even if he visits URIs that do not contain version information.

To support that scenario for custom version catalog pages, a new DocVersionLink React component was added to @docusaurus/theme-classic module. It can be then used in a custom versions.mdx page, for example:

import DocVersionLink from '@theme/DocVersionLink';

# Documentation Versions

## Current Version

| Version | Release Date | | |
|:-|:-|:-|:-|
| 2024.3 | December 31, 2024 | <DocVersionLink to="docs">Documentation</DocVersionLink> | [Release Notes](#) |

## Previous Versions

### 2024

| Version | Release Date | | |
|:-|:-|:-|:-|
| 2024.2 | September 17, 2024 | <DocVersionLink to="docs/2024.2">Documentation</DocVersionLink> | [Release Notes](#) |
| 2024.1 | March 29, 2024 | <DocVersionLink to="docs/2024.1">Documentation</DocVersionLink> | [Release Notes](#) |

### 2023

| Version | Release Date | | |
|:-|:-|:-|:-|
| 2023.4 | November 29, 2023 | <DocVersionLink to="docs/2023.4">Documentation</DocVersionLink> | [Release Notes](#) |
| 2023.3 | August 9, 2023 | <DocVersionLink to="docs/2023.3">Documentation</DocVersionLink> | [Release Notes](#) |
| 2023.2 | April 30, 2023 | <DocVersionLink to="docs/2023.2">Documentation</DocVersionLink> | [Release Notes](#) |
| 2023.1 | January 5, 2023 | <DocVersionLink to="docs/2023.1">Documentation</DocVersionLink> | [Release Notes](#) |

Internally, DocVersionLink component analyzes the target URI, and if it finds an associated versioned content, it injects a corresponding storage persistence logic. DocVersionLink works transparently to a user, so there is no need to specify plugin identifiers manually. Everything is handled automatically.

You can see the version persistence in action here.

Self-service

  • I'd be willing to contribute this feature to Docusaurus myself.

Activity

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Assignees

No one assigned

    Labels

    featureThis is not a bug or issue with Docusausus, per se. It is a feature request for the future.

    Type

    No type

    Projects

    No projects

    Milestone

    No milestone

    Relationships

    None yet

    Development

    No branches or pull requests

    Issue actions