Compute productGroups children hrefs on server (#40232)
This commit is contained in:
@@ -38,9 +38,8 @@ for (const productId of productIds) {
|
||||
toc,
|
||||
wip: data.wip || false,
|
||||
hidden: data.hidden || false,
|
||||
versions: applicableVersions,
|
||||
}
|
||||
|
||||
internalProducts[productId].versions = applicableVersions
|
||||
}
|
||||
|
||||
export const productMap = Object.assign({}, internalProducts, externalProducts)
|
||||
|
||||
@@ -3,27 +3,53 @@ import path from 'path'
|
||||
import { productMap, data } from './all-products.js'
|
||||
import { renderContentWithFallback } from './render-with-fallback.js'
|
||||
import removeFPTFromPath from './remove-fpt-from-path.js'
|
||||
import getApplicableVersions from './get-applicable-versions.js'
|
||||
|
||||
async function getPage(id, lang, pageMap, context) {
|
||||
const productId = id.split('/')[0]
|
||||
const product = productMap[productId]
|
||||
const external = product.external || false // undefined becomes false
|
||||
// Adding external links to a product group here due to accessibility design changes
|
||||
// where we removed the sidebar on the homepage - docs-team 2965
|
||||
const href = external
|
||||
? product.href
|
||||
: removeFPTFromPath(path.posix.join('/', lang, product.versions[0], id))
|
||||
|
||||
// The href depends. Initially all we have is an `id` which might be
|
||||
// something like 'code-security/dependabot'.
|
||||
// To get from that to a Page instance, we have to "guess" what the
|
||||
// href might be.
|
||||
// If URL currently is `/fr/enterprise-server@3.9`,
|
||||
// we're going to try `/fr/enterprise-server@3.9/code-security/dependabot`
|
||||
// first. And if the URL is `/en` we'll try `/en/code-security/dependabot`.
|
||||
// But some pages are not available in all versions.
|
||||
// So we have to try `product.versions[0]` which comes from the `productMap`
|
||||
// (not be confused with the `pageMap`!)
|
||||
// Once we have a page, we can get to its `.applicableVersions`.
|
||||
// This way, we get the best of both worlds. We use the `currentVersion`
|
||||
// if it's applicable, but we fall back to the first version if it's not.
|
||||
let href = product.href
|
||||
|
||||
let name = product.name
|
||||
let versions = getApplicableVersions('*')
|
||||
|
||||
if (!external) {
|
||||
// First we have to find it as a page object based on its ID.
|
||||
href = removeFPTFromPath(path.posix.join('/', lang, context.currentVersion, id))
|
||||
if (!pageMap[href]) {
|
||||
// If the page is not available in the *current* version, we
|
||||
// fall back it its default version, which is `product.versions[0]`.
|
||||
// For example, you're on `/en/enterprise-server@3.1` and you're
|
||||
// but a `/foo/bar` is only available in `enterprise-cloud@latest`.
|
||||
href = removeFPTFromPath(path.posix.join('/', lang, product.versions[0], id))
|
||||
}
|
||||
const page = pageMap[href]
|
||||
if (!page) {
|
||||
throw new Error(
|
||||
`Unable to find a page by the href '${href}'. Review your 'childGroups' frontmatter maybe.`,
|
||||
`Unable to find a page by the href '${href}'. Review your 'childGroups' front matter.`,
|
||||
)
|
||||
}
|
||||
|
||||
// Some should not be included for the current version, and returning
|
||||
// undefined here means this entry will be filtered out by the caller.
|
||||
const isFPT = context.currentVersion === 'free-pro-team@latest'
|
||||
if (!isFPT && !page.applicableVersions.includes(context.currentVersion)) {
|
||||
return
|
||||
}
|
||||
|
||||
if (page.rawShortTitle) {
|
||||
name = await renderContentWithFallback(page, 'rawShortTitle', context, {
|
||||
textOnly: true,
|
||||
@@ -37,16 +63,13 @@ async function getPage(id, lang, pageMap, context) {
|
||||
textOnly: true,
|
||||
})
|
||||
}
|
||||
|
||||
versions = page.applicableVersions
|
||||
}
|
||||
// Return only the props needed for the ProductSelectionCard, since
|
||||
// that's the only place this is ever used.
|
||||
return {
|
||||
id,
|
||||
name,
|
||||
href: href.replace(`/${lang}/`, '/'),
|
||||
versions,
|
||||
href,
|
||||
external,
|
||||
}
|
||||
}
|
||||
@@ -59,9 +82,9 @@ export async function getProductGroups(pageMap, lang, context) {
|
||||
icon: group.icon || null,
|
||||
octicon: group.octicon || null,
|
||||
// Typically the children are product IDs, but we support deeper page paths too
|
||||
children: await Promise.all(
|
||||
group.children.map((id) => getPage(id, lang, pageMap, context)),
|
||||
),
|
||||
children: (
|
||||
await Promise.all(group.children.map((id) => getPage(id, lang, pageMap, context)))
|
||||
).filter(Boolean),
|
||||
}
|
||||
}),
|
||||
)
|
||||
|
||||
Reference in New Issue
Block a user