This is an automated email from the ASF dual-hosted git repository.
jeffreyh pushed a commit to branch master
in repository https://gitbox.apache.org/repos/asf/doris-website.git
The following commit(s) were added to refs/heads/master by this push:
new 204f988257c fix:request when switch version (#1470)
204f988257c is described below
commit 204f988257cce3dbca419e5577361897970545ae
Author: yangon <[email protected]>
AuthorDate: Fri Dec 6 14:41:04 2024 +0800
fix:request when switch version (#1470)
Co-authored-by: liyang <[email protected]>
---
src/theme/SearchBar/SearchBar.jsx | 373 ++++++++++++++++++++++----------------
1 file changed, 213 insertions(+), 160 deletions(-)
diff --git a/src/theme/SearchBar/SearchBar.jsx
b/src/theme/SearchBar/SearchBar.jsx
index a82ab78e15e..f80b948d72a 100644
--- a/src/theme/SearchBar/SearchBar.jsx
+++ b/src/theme/SearchBar/SearchBar.jsx
@@ -1,36 +1,51 @@
-import React, { useCallback, useEffect, useRef, useState, } from "react";
-import clsx from "clsx";
-import useDocusaurusContext from "@docusaurus/useDocusaurusContext";
-import useIsBrowser from "@docusaurus/useIsBrowser";
-import { useHistory, useLocation } from "@docusaurus/router";
-import { translate } from "@docusaurus/Translate";
-import { ReactContextError, useDocsPreferredVersion, } from
"@docusaurus/theme-common";
-import { useActivePlugin } from "@docusaurus/plugin-content-docs/client";
-import { fetchIndexes } from "./fetchIndexes";
-import { SearchSourceFactory } from "../../utils/SearchSourceFactory";
-import { SuggestionTemplate } from "./SuggestionTemplate";
-import { EmptyTemplate } from "./EmptyTemplate";
-import { searchResultLimits, Mark, searchBarShortcut, searchBarShortcutHint,
searchBarPosition, docsPluginIdForPreferredVersion, indexDocs,
searchContextByPaths, hideSearchBarWithNoSearchContext,
useAllContextsWithNoSearchContext, } from "../../utils/proxiedGenerated";
-import LoadingRing from "../LoadingRing/LoadingRing";
-import styles from "./SearchBar.module.css";
-import { normalizeContextByPath } from "../../utils/normalizeContextByPath";
+import React, { useCallback, useEffect, useRef, useState } from 'react';
+import clsx from 'clsx';
+import useDocusaurusContext from '@docusaurus/useDocusaurusContext';
+import useIsBrowser from '@docusaurus/useIsBrowser';
+import { useHistory, useLocation } from '@docusaurus/router';
+import { translate } from '@docusaurus/Translate';
+import { ReactContextError, useDocsPreferredVersion } from
'@docusaurus/theme-common';
+import { useActivePlugin } from '@docusaurus/plugin-content-docs/client';
+import { fetchIndexes } from './fetchIndexes';
+import { SearchSourceFactory } from '../../utils/SearchSourceFactory';
+import { SuggestionTemplate } from './SuggestionTemplate';
+import { EmptyTemplate } from './EmptyTemplate';
+import {
+ searchResultLimits,
+ Mark,
+ searchBarShortcut,
+ searchBarShortcutHint,
+ searchBarPosition,
+ docsPluginIdForPreferredVersion,
+ indexDocs,
+ searchContextByPaths,
+ hideSearchBarWithNoSearchContext,
+ useAllContextsWithNoSearchContext,
+} from '../../utils/proxiedGenerated';
+import LoadingRing from '../LoadingRing/LoadingRing';
+import { VERSIONS, DEFAULT_VERSION } from '@site/src/constant/common';
+import styles from './SearchBar.module.css';
+import { normalizeContextByPath } from '../../utils/normalizeContextByPath';
async function fetchAutoCompleteJS() {
- const autoCompleteModule = await import("@easyops-cn/autocomplete.js");
+ const autoCompleteModule = await import('@easyops-cn/autocomplete.js');
const autoComplete = autoCompleteModule.default;
if (autoComplete.noConflict) {
// For webpack v5 since docusaurus v2.0.0-alpha.75
autoComplete.noConflict();
- }
- else if (autoCompleteModule.noConflict) {
+ } else if (autoCompleteModule.noConflict) {
// For webpack v4 before docusaurus v2.0.0-alpha.74
autoCompleteModule.noConflict();
}
return autoComplete;
}
-const SEARCH_PARAM_HIGHLIGHT = "_highlight";
-export default function SearchBar({ handleSearchBarToggle, }) {
+const SEARCH_PARAM_HIGHLIGHT = '_highlight';
+export default function SearchBar({ handleSearchBarToggle }) {
const isBrowser = useIsBrowser();
- const { siteConfig: { baseUrl }, i18n: { currentLocale }, } =
useDocusaurusContext();
+ const [curVersion, setCurVersion] = useState(DEFAULT_VERSION);
+ const {
+ siteConfig: { baseUrl },
+ i18n: { currentLocale },
+ } = useDocusaurusContext();
// It returns undefined for non-docs pages
const activePlugin = useActivePlugin();
let versionUrl = baseUrl;
@@ -45,15 +60,13 @@ export default function SearchBar({ handleSearchBarToggle,
}) {
// eslint-disable-next-line react-hooks/rules-of-hooks
const { preferredVersion } =
useDocsPreferredVersion(activePlugin?.pluginId ??
docsPluginIdForPreferredVersion);
if (preferredVersion && !preferredVersion.isLast) {
- versionUrl = preferredVersion.path + "/";
+ versionUrl = preferredVersion.path + '/';
}
- }
- catch (e) {
+ } catch (e) {
if (indexDocs) {
if (e instanceof ReactContextError) {
/* ignore, happens when website doesn't use versions */
- }
- else {
+ } else {
throw e;
}
}
@@ -66,20 +79,20 @@ export default function SearchBar({ handleSearchBarToggle,
}) {
const focusAfterIndexLoaded = useRef(false);
const [loading, setLoading] = useState(false);
const [inputChanged, setInputChanged] = useState(false);
- const [inputValue, setInputValue] = useState("");
+ const [inputValue, setInputValue] = useState('');
const search = useRef(null);
- const prevSearchContext = useRef("");
- const [searchContext, setSearchContext] = useState("");
+ const prevSearchContext = useRef('');
+ const [searchContext, setSearchContext] = useState('');
useEffect(() => {
if (!Array.isArray(searchContextByPaths)) {
return;
}
- let nextSearchContext = "";
+ let nextSearchContext = '';
if (location.pathname.startsWith(versionUrl)) {
const uri = location.pathname.substring(versionUrl.length);
let matchedPath;
for (const _path of searchContextByPaths) {
- const path = typeof _path === "string" ? _path : _path.path;
+ const path = typeof _path === 'string' ? _path : _path.path;
if (uri === path || uri.startsWith(`${path}/`)) {
matchedPath = path;
break;
@@ -96,69 +109,76 @@ export default function SearchBar({ handleSearchBarToggle,
}) {
}
setSearchContext(nextSearchContext);
}, [location.pathname, versionUrl]);
- const hidden = !!hideSearchBarWithNoSearchContext &&
- Array.isArray(searchContextByPaths) &&
- searchContext === "";
- const loadIndex = useCallback(async () => {
- if (hidden || indexStateMap.current.get(searchContext)) {
+ const hidden = !!hideSearchBarWithNoSearchContext &&
Array.isArray(searchContextByPaths) && searchContext === '';
+ const loadIndex = useCallback(async (forceLoad = false) => {
+ if ((hidden || indexStateMap.current.get(searchContext)) &&
!forceLoad) {
// Do not load the index (again) if its already loaded or in the
process of being loaded.
return;
}
- indexStateMap.current.set(searchContext, "loading");
+ indexStateMap.current.set(searchContext, 'loading');
search.current?.autocomplete.destroy();
setLoading(true);
const [{ wrappedIndexes, zhDictionary }, autoComplete] = await
Promise.all([
fetchIndexes(versionUrl, searchContext),
fetchAutoCompleteJS(),
]);
- const searchFooterLinkElement = ({ query, isEmpty, }) => {
- const a = document.createElement("a");
+ const searchFooterLinkElement = ({ query, isEmpty }) => {
+ const a = document.createElement('a');
const params = new URLSearchParams();
- params.set("q", query);
+ params.set('q', query);
let linkText;
if (searchContext) {
- const detailedSearchContext = searchContext &&
Array.isArray(searchContextByPaths)
- ? searchContextByPaths.find((item) => typeof item ===
"string"
- ? item === searchContext
- : item.path === searchContext)
- : searchContext;
+ const detailedSearchContext =
+ searchContext && Array.isArray(searchContextByPaths)
+ ? searchContextByPaths.find(item =>
+ typeof item === 'string' ? item ===
searchContext : item.path === searchContext,
+ )
+ : searchContext;
const translatedSearchContext = detailedSearchContext
? normalizeContextByPath(detailedSearchContext,
currentLocale).label
: searchContext;
if (useAllContextsWithNoSearchContext && isEmpty) {
- linkText = translate({
- id: "theme.SearchBar.seeAllOutsideContext",
- message: 'See all results outside "{context}"',
- }, { context: translatedSearchContext });
- }
- else {
- linkText = translate({
- id: "theme.SearchBar.searchInContext",
- message: 'See all results within "{context}"',
- }, { context: translatedSearchContext });
+ linkText = translate(
+ {
+ id: 'theme.SearchBar.seeAllOutsideContext',
+ message: 'See all results outside "{context}"',
+ },
+ { context: translatedSearchContext },
+ );
+ } else {
+ linkText = translate(
+ {
+ id: 'theme.SearchBar.searchInContext',
+ message: 'See all results within "{context}"',
+ },
+ { context: translatedSearchContext },
+ );
}
- }
- else {
+ } else {
linkText = translate({
- id: "theme.SearchBar.seeAll",
- message: "See all results",
+ id: 'theme.SearchBar.seeAll',
+ message: 'See all results',
});
}
- if (searchContext &&
+ if (
+ searchContext &&
Array.isArray(searchContextByPaths) &&
- (!useAllContextsWithNoSearchContext || !isEmpty)) {
- params.set("ctx", searchContext);
+ (!useAllContextsWithNoSearchContext || !isEmpty)
+ ) {
+ params.set('ctx', searchContext);
}
if (versionUrl !== baseUrl) {
if (!versionUrl.startsWith(baseUrl)) {
- throw new Error(`Version url '${versionUrl}' does not
start with base url '${baseUrl}', this is a bug of
\`@easyops-cn/docusaurus-search-local\`, please report it.`);
+ throw new Error(
+ `Version url '${versionUrl}' does not start with base
url '${baseUrl}', this is a bug of \`@easyops-cn/docusaurus-search-local\`,
please report it.`,
+ );
}
- params.set("version", versionUrl.substring(baseUrl.length));
+ params.set('version', versionUrl.substring(baseUrl.length));
}
const url = `${baseUrl}search/?${params.toString()}`;
a.href = url;
a.textContent = linkText;
- a.addEventListener("click", (e) => {
+ a.addEventListener('click', e => {
if (!e.ctrlKey && !e.metaKey) {
e.preventDefault();
search.current?.autocomplete.close();
@@ -167,63 +187,66 @@ export default function SearchBar({
handleSearchBarToggle, }) {
});
return a;
};
- search.current = autoComplete(searchBarRef.current, {
- hint: false,
- autoselect: true,
- openOnFocus: true,
- cssClasses: {
- root: clsx(styles.searchBar, {
- [styles.searchBarLeft]: searchBarPosition === "left",
- }),
- noPrefix: true,
- dropdownMenu: styles.dropdownMenu,
- input: styles.input,
- hint: styles.hint,
- suggestions: styles.suggestions,
- suggestion: styles.suggestion,
- cursor: styles.cursor,
- dataset: styles.dataset,
- empty: styles.empty,
- },
- }, [
+ search.current = autoComplete(
+ searchBarRef.current,
{
- source: SearchSourceFactory(wrappedIndexes, zhDictionary,
searchResultLimits),
- templates: {
- suggestion: SuggestionTemplate,
- empty: EmptyTemplate,
- footer: ({ query, isEmpty }) => {
- if (isEmpty &&
- (!searchContext ||
!useAllContextsWithNoSearchContext)) {
- return;
- }
- const a = searchFooterLinkElement({ query, isEmpty });
- const div = document.createElement("div");
- div.className = styles.hitFooter;
- div.appendChild(a);
- return div;
- },
+ hint: false,
+ autoselect: true,
+ openOnFocus: true,
+ cssClasses: {
+ root: clsx(styles.searchBar, {
+ [styles.searchBarLeft]: searchBarPosition === 'left',
+ }),
+ noPrefix: true,
+ dropdownMenu: styles.dropdownMenu,
+ input: styles.input,
+ hint: styles.hint,
+ suggestions: styles.suggestions,
+ suggestion: styles.suggestion,
+ cursor: styles.cursor,
+ dataset: styles.dataset,
+ empty: styles.empty,
},
},
- ])
- .on("autocomplete:selected", function (event, { document: { u, h
}, tokens }) {
- searchBarRef.current?.blur();
- let url = u;
- if (Mark && tokens.length > 0) {
- const params = new URLSearchParams();
- for (const token of tokens) {
- params.append(SEARCH_PARAM_HIGHLIGHT, token);
+ [
+ {
+ source: SearchSourceFactory(wrappedIndexes, zhDictionary,
searchResultLimits),
+ templates: {
+ suggestion: SuggestionTemplate,
+ empty: EmptyTemplate,
+ footer: ({ query, isEmpty }) => {
+ if (isEmpty && (!searchContext ||
!useAllContextsWithNoSearchContext)) {
+ return;
+ }
+ const a = searchFooterLinkElement({ query, isEmpty
});
+ const div = document.createElement('div');
+ div.className = styles.hitFooter;
+ div.appendChild(a);
+ return div;
+ },
+ },
+ },
+ ],
+ )
+ .on('autocomplete:selected', function (event, { document: { u, h
}, tokens }) {
+ searchBarRef.current?.blur();
+ let url = u;
+ if (Mark && tokens.length > 0) {
+ const params = new URLSearchParams();
+ for (const token of tokens) {
+ params.append(SEARCH_PARAM_HIGHLIGHT, token);
+ }
+ url += `?${params.toString()}`;
}
- url += `?${params.toString()}`;
- }
- if (h) {
- url += h;
- }
- history.push(url);
- })
- .on("autocomplete:closed", () => {
- searchBarRef.current?.blur();
- });
- indexStateMap.current.set(searchContext, "done");
+ if (h) {
+ url += h;
+ }
+ history.push(url);
+ })
+ .on('autocomplete:closed', () => {
+ searchBarRef.current?.blur();
+ });
+ indexStateMap.current.set(searchContext, 'done');
setLoading(false);
if (focusAfterIndexLoaded.current) {
const input = searchBarRef.current;
@@ -237,15 +260,13 @@ export default function SearchBar({
handleSearchBarToggle, }) {
if (!Mark) {
return;
}
- const keywords = isBrowser
- ? new
URLSearchParams(location.search).getAll(SEARCH_PARAM_HIGHLIGHT)
- : [];
+ const keywords = isBrowser ? new
URLSearchParams(location.search).getAll(SEARCH_PARAM_HIGHLIGHT) : [];
// A workaround to fix an issue of highlighting in code blocks.
// See https://github.com/easyops-cn/docusaurus-search-local/issues/92
// Code blocks will be re-rendered after this `useEffect` ran.
// So we make the marking run after a macro task.
setTimeout(() => {
- const root = document.querySelector("article");
+ const root = document.querySelector('article');
if (!root) {
return;
}
@@ -255,8 +276,8 @@ export default function SearchBar({ handleSearchBarToggle,
}) {
mark.mark(keywords);
}
// Apply any keywords to the search input so that we can clear
marks in case we loaded a page with a highlight in the url
- setInputValue(keywords.join(" "));
- search.current?.autocomplete.setVal(keywords.join(" "));
+ setInputValue(keywords.join(' '));
+ search.current?.autocomplete.setVal(keywords.join(' '));
});
}, [isBrowser, location.search, location.pathname]);
const [focused, setFocused] = useState(false);
@@ -273,67 +294,99 @@ export default function SearchBar({
handleSearchBarToggle, }) {
const onInputMouseEnter = useCallback(() => {
loadIndex();
}, [loadIndex]);
- const onInputChange = useCallback((event) => {
+ const onInputChange = useCallback(event => {
setInputValue(event.target.value);
if (event.target.value) {
setInputChanged(true);
}
}, []);
// Implement hint icons for the search shortcuts on mac and the rest
operating systems.
- const isMac = isBrowser
- ? /mac/i.test(navigator.userAgentData?.platform ?? navigator.platform)
- : false;
+ const isMac = isBrowser ? /mac/i.test(navigator.userAgentData?.platform ??
navigator.platform) : false;
+
+ useEffect(() => {
+ const pathHaveVer = VERSIONS.some(item =>
location.pathname.includes(item));
+ if (!pathHaveVer && curVersion !== '2.1') {
+ setCurVersion('2.1');
+ } else {
+ VERSIONS.forEach(item => {
+ if (location.pathname.includes(item) && item !== curVersion) {
+ setCurVersion(item);
+ }
+ });
+ }
+ }, [location.pathname]);
+ useEffect(() => {
+ loadIndex(true);
+ }, [curVersion]);
useEffect(() => {
if (!searchBarShortcut) {
return;
}
// Add shortcuts command/ctrl + K
- const handleShortcut = (event) => {
- if ((isMac ? event.metaKey : event.ctrlKey) &&
- (event.key === "k" || event.key === "K")) {
+ const handleShortcut = event => {
+ if ((isMac ? event.metaKey : event.ctrlKey) && (event.key === 'k'
|| event.key === 'K')) {
event.preventDefault();
searchBarRef.current?.focus();
onInputFocus();
}
};
- document.addEventListener("keydown", handleShortcut);
+ document.addEventListener('keydown', handleShortcut);
return () => {
- document.removeEventListener("keydown", handleShortcut);
+ document.removeEventListener('keydown', handleShortcut);
};
}, [isMac, onInputFocus]);
const onClearSearch = useCallback(() => {
const params = new URLSearchParams(location.search);
params.delete(SEARCH_PARAM_HIGHLIGHT);
const paramsStr = params.toString();
- const searchUrl = location.pathname +
- (paramsStr != "" ? `?${paramsStr}` : "") +
- location.hash;
+ const searchUrl = location.pathname + (paramsStr != '' ?
`?${paramsStr}` : '') + location.hash;
if (searchUrl != location.pathname + location.search + location.hash) {
history.push(searchUrl);
}
// We always clear these here because in case no match was selected
the above history push wont happen
- setInputValue("");
- search.current?.autocomplete.setVal("");
+ setInputValue('');
+ search.current?.autocomplete.setVal('');
}, [location.pathname, location.search, location.hash, history]);
- return (<div className={clsx("navbar__search", styles.searchBarContainer, {
- [styles.searchIndexLoading]: loading && inputChanged,
- [styles.focused]: focused,
- })} hidden={hidden}
- // Manually make the search bar be LTR even if in RTL
- dir="ltr">
- <input placeholder={translate({
- id: "theme.SearchBar.label",
- message: "Search",
- description: "The ARIA label and placeholder for search button",
- })} aria-label="Search" className="navbar__search-input"
onMouseEnter={onInputMouseEnter} onFocus={onInputFocus} onBlur={onInputBlur}
onChange={onInputChange} ref={searchBarRef} value={inputValue}/>
- <LoadingRing className={styles.searchBarLoadingRing}/>
- {searchBarShortcut &&
- searchBarShortcutHint &&
- (inputValue !== "" ? (<button className={styles.searchClearButton}
onClick={onClearSearch}>
- ✕
- </button>) : (isBrowser && (<div
className={styles.searchHintContainer}>
- <kbd className={styles.searchHint}>{isMac ? "⌘" : "ctrl"}</kbd>
- <kbd className={styles.searchHint}>K</kbd>
- </div>)))}
- </div>);
+ return (
+ <div
+ className={clsx('navbar__search', styles.searchBarContainer, {
+ [styles.searchIndexLoading]: loading && inputChanged,
+ [styles.focused]: focused,
+ })}
+ hidden={hidden}
+ // Manually make the search bar be LTR even if in RTL
+ dir="ltr"
+ >
+ <input
+ placeholder={translate({
+ id: 'theme.SearchBar.label',
+ message: 'Search',
+ description: 'The ARIA label and placeholder for search
button',
+ })}
+ aria-label="Search"
+ className="navbar__search-input"
+ onMouseEnter={onInputMouseEnter}
+ onFocus={onInputFocus}
+ onBlur={onInputBlur}
+ onChange={onInputChange}
+ ref={searchBarRef}
+ value={inputValue}
+ />
+ <LoadingRing className={styles.searchBarLoadingRing} />
+ {searchBarShortcut &&
+ searchBarShortcutHint &&
+ (inputValue !== '' ? (
+ <button className={styles.searchClearButton}
onClick={onClearSearch}>
+ ✕
+ </button>
+ ) : (
+ isBrowser && (
+ <div className={styles.searchHintContainer}>
+ <kbd className={styles.searchHint}>{isMac ? '⌘' :
'ctrl'}</kbd>
+ <kbd className={styles.searchHint}>K</kbd>
+ </div>
+ )
+ ))}
+ </div>
+ );
}
---------------------------------------------------------------------
To unsubscribe, e-mail: [email protected]
For additional commands, e-mail: [email protected]