HiDeoo / starlight-openapi

Starlight plugin to generate documentation from OpenAPI/Swagger specifications
https://starlight-openapi.vercel.app
MIT License
90 stars 9 forks source link

Compatibility with Internationalization (i18n) #37

Open dealmengor opened 4 days ago

dealmengor commented 4 days ago

Is your feature request related to a problem?

I need to write a documentation in two languages, starlight have by default this support and works great; however the autogenerated routes and pages based on the opeanapi yaml, I wasn't able to create a version in both languages.

Describe the solution you'd like

I would like an easy way to read for example .yaml file in Spanish and another one in English and it make compatible with the Internationalization (i18n) from the Astro starlight template.

Describe alternatives you've considered

I almost find a workaround by my own but wasn't possible.

  1. I created two sub-folders inside schemas folder: ES, EN
  2. Inside the folder add the documentation for example: schemas/en/pad.yaml and schemas/es/pad.yaml
  3. Then in the astro.config.mjs file do something like this:
      plugins: [
          // Generate the OpenAPI documentation pages.
          starlightOpenAPI([
              {
                  base: 'services-pad',
                  label: 'PAD',
                  schema: 'schemas/en/pad.yaml',
              },
              {
                  base: 'services-pad',
                  label: 'PAD',
                  schema: 'schemas/es/pad.yaml',
              }
          ]),
      ],
  4. And the sidebar array was like this:
      sidebar: [
          {
              label: '📚 Guías',
              items: [{ label: 'Introducción', link: '/guides/intro/' }],
          },
          {
              // Add the generated sidebar group to the sidebar.
              label: '🛠️ Services',
              badge: { text: 'New', variant: 'note' },
              items: [
                  ...openAPISidebarGroups,],
          }
      ],
  5. It work because generated the /es/ routes but in the menu was redundant, I tried to modify but I wasn't able to do it, could be nice a way to avoid this duplicate menu entry, and also this support can work with multiple schemas.
  6. Epic fail result... image

Additional Context

Thanks in advance and nice work doing this plugin!

HiDeoo commented 4 days ago

Thanks for your report :raised_hands:

There are at the moment some ongoing refactoring in Starlight to improve/refactor some Internationalization support which also targets plugins and improve i18n support in plugins (which was not really possible before). When this is done, this plugin will be updated and refactored to work with such features as I did not want to "hack" around the current implementation as a temporary solution that would be broken in the near future.

Until then, I think something similar to your workaround could work. Let's say for example the 2 schemas had different labels, e.g. "PAD (en)" and "PAD (es)", you could use a component override for the <Sidebar> component and filter out the group you want to remove based on the current language.

This could look something like this:

---
// src/overrides/Sidebar.astro
import type { Props } from '@astrojs/starlight/props';
import Default from '@astrojs/starlight/components/Sidebar.astro';

const isEnglishPage = Astro.url.pathname.startsWith('/en/');

Astro.props.sidebar = Astro.props.sidebar
  .filter((entry) => (
    // Filter out the group with the label "PAD (es)" if the current page is in English
    if (isEnglishPage && entry.type === 'group' && entry.label === 'PAD (es)') {
      return false;
    } else if (!isEnglishPage && entry.type === 'group' && entry.label === 'PAD (en)') {
      // or filter out the group with the label "PAD (en)" if the current page is not in English
      return false;
    }

    return true
  ));
---

<Default {...Astro.props}><slot /></Default>