mirror of
https://github.com/Snigdha-OS/documentation.git
synced 2025-12-25 07:23:50 +01:00
144 lines
4.7 KiB
JavaScript
144 lines
4.7 KiB
JavaScript
/**
|
|
* Copyright (c) Facebook, Inc. and its affiliates.
|
|
*
|
|
* This source code is licensed under the MIT license found in the
|
|
* LICENSE file in the root directory of this source tree.
|
|
*/
|
|
import React from 'react';
|
|
import Head from '@docusaurus/Head';
|
|
import useDocusaurusContext from '@docusaurus/useDocusaurusContext';
|
|
import useBaseUrl from '@docusaurus/useBaseUrl';
|
|
import {PageMetadata, useThemeConfig} from '@docusaurus/theme-common';
|
|
import {
|
|
DEFAULT_SEARCH_TAG,
|
|
useAlternatePageUtils,
|
|
keyboardFocusedClassName,
|
|
} from '@docusaurus/theme-common/internal';
|
|
import {useLocation} from '@docusaurus/router';
|
|
import {applyTrailingSlash} from '@docusaurus/utils-common';
|
|
import SearchMetadata from '@theme/SearchMetadata';
|
|
// TODO move to SiteMetadataDefaults or theme-common ?
|
|
// Useful for i18n/SEO
|
|
// See https://developers.google.com/search/docs/advanced/crawling/localized-versions
|
|
// See https://github.com/facebook/docusaurus/issues/3317
|
|
function AlternateLangHeaders() {
|
|
const {
|
|
i18n: {currentLocale, defaultLocale, localeConfigs},
|
|
} = useDocusaurusContext();
|
|
const alternatePageUtils = useAlternatePageUtils();
|
|
const currentHtmlLang = localeConfigs[currentLocale].htmlLang;
|
|
// HTML lang is a BCP 47 tag, but the Open Graph protocol requires
|
|
// using underscores instead of dashes.
|
|
// See https://ogp.me/#optional
|
|
// See https://en.wikipedia.org/wiki/IETF_language_tag)
|
|
const bcp47ToOpenGraphLocale = (code) => code.replace('-', '_');
|
|
// Note: it is fine to use both "x-default" and "en" to target the same url
|
|
// See https://www.searchviu.com/en/multiple-hreflang-tags-one-url/
|
|
return (
|
|
<Head>
|
|
{Object.entries(localeConfigs).map(([locale, {htmlLang}]) => (
|
|
<link
|
|
key={locale}
|
|
rel="alternate"
|
|
href={alternatePageUtils.createUrl({
|
|
locale,
|
|
fullyQualified: true,
|
|
})}
|
|
hrefLang={htmlLang}
|
|
/>
|
|
))}
|
|
<link
|
|
rel="alternate"
|
|
href={alternatePageUtils.createUrl({
|
|
locale: defaultLocale,
|
|
fullyQualified: true,
|
|
})}
|
|
hrefLang="x-default"
|
|
/>
|
|
|
|
<meta
|
|
property="og:locale"
|
|
content={bcp47ToOpenGraphLocale(currentHtmlLang)}
|
|
/>
|
|
{Object.values(localeConfigs)
|
|
.filter((config) => currentHtmlLang !== config.htmlLang)
|
|
.map((config) => (
|
|
<meta
|
|
key={`meta-og-${config.htmlLang}`}
|
|
property="og:locale:alternate"
|
|
content={bcp47ToOpenGraphLocale(config.htmlLang)}
|
|
/>
|
|
))}
|
|
</Head>
|
|
);
|
|
}
|
|
// Default canonical url inferred from current page location pathname
|
|
function useDefaultCanonicalUrl() {
|
|
const {
|
|
siteConfig: {url: siteUrl, baseUrl, trailingSlash},
|
|
} = useDocusaurusContext();
|
|
// TODO using useLocation().pathname is not a super idea
|
|
// See https://github.com/facebook/docusaurus/issues/9170
|
|
const {pathname} = useLocation();
|
|
const canonicalPathname = applyTrailingSlash(useBaseUrl(pathname), {
|
|
trailingSlash,
|
|
baseUrl,
|
|
});
|
|
return siteUrl + canonicalPathname;
|
|
}
|
|
// TODO move to SiteMetadataDefaults or theme-common ?
|
|
function CanonicalUrlHeaders({permalink}) {
|
|
const {
|
|
siteConfig: {url: siteUrl},
|
|
} = useDocusaurusContext();
|
|
const defaultCanonicalUrl = useDefaultCanonicalUrl();
|
|
const canonicalUrl = permalink
|
|
? `${siteUrl}${permalink}`
|
|
: defaultCanonicalUrl;
|
|
return (
|
|
<Head>
|
|
<meta property="og:url" content={canonicalUrl} />
|
|
<link rel="canonical" href={canonicalUrl} />
|
|
</Head>
|
|
);
|
|
}
|
|
export default function SiteMetadata() {
|
|
const {
|
|
i18n: {currentLocale},
|
|
} = useDocusaurusContext();
|
|
// TODO maybe move these 2 themeConfig to siteConfig?
|
|
// These seems useful for other themes as well
|
|
const {metadata, image: defaultImage} = useThemeConfig();
|
|
return (
|
|
<>
|
|
<Head>
|
|
<meta name="twitter:card" content="summary_large_image" />
|
|
{/* The keyboard focus class name need to be applied when SSR so links
|
|
are outlined when JS is disabled */}
|
|
<body className={keyboardFocusedClassName} />
|
|
</Head>
|
|
|
|
{defaultImage && <PageMetadata image={defaultImage} />}
|
|
|
|
<CanonicalUrlHeaders />
|
|
|
|
<AlternateLangHeaders />
|
|
|
|
<SearchMetadata tag={DEFAULT_SEARCH_TAG} locale={currentLocale} />
|
|
|
|
{/*
|
|
It's important to have an additional <Head> element here, as it allows
|
|
react-helmet to override default metadata values set in previous <Head>
|
|
like "twitter:card". In same Head, the same meta would appear twice
|
|
instead of overriding.
|
|
*/}
|
|
<Head>
|
|
{/* Yes, "metadatum" is the grammatically correct term */}
|
|
{metadata.map((metadatum, i) => (
|
|
<meta key={i} {...metadatum} />
|
|
))}
|
|
</Head>
|
|
</>
|
|
);
|
|
}
|