@easyops-cn/docusaurus-search-local 0.48.4 → 0.49.0
This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
- package/CHANGELOG.md +14 -0
- package/dist/client/client/theme/SearchBar/SearchBar.jsx +6 -0
- package/dist/client/client/theme/worker.js +3 -0
- package/dist/client/client/utils/__mocks__/proxiedGeneratedConstants.js +4 -0
- package/dist/client/client/utils/smartQueries.js +32 -18
- package/dist/server/server/utils/generate.js +2 -2
- package/dist/server/server/utils/validateOptions.js +1 -0
- package/dist/types/index.d.ts +7 -0
- package/package.json +1 -1
package/CHANGELOG.md
CHANGED
|
@@ -2,6 +2,20 @@
|
|
|
2
2
|
|
|
3
3
|
All notable changes to this project will be documented in this file. See [standard-version](https://github.com/conventional-changelog/standard-version) for commit guidelines.
|
|
4
4
|
|
|
5
|
+
## [0.49.0](https://github.com/easyops-cn/docusaurus-search-local/compare/v0.48.5...v0.49.0) (2025-03-12)
|
|
6
|
+
|
|
7
|
+
|
|
8
|
+
### Features
|
|
9
|
+
|
|
10
|
+
* support fuzzy matching, closes [#504](https://github.com/easyops-cn/docusaurus-search-local/issues/504) ([#505](https://github.com/easyops-cn/docusaurus-search-local/issues/505)) ([c8310f3](https://github.com/easyops-cn/docusaurus-search-local/commit/c8310f39c05f0409ba227318a70dba828ca65aa0))
|
|
11
|
+
|
|
12
|
+
## [0.48.5](https://github.com/easyops-cn/docusaurus-search-local/compare/v0.48.4...v0.48.5) (2025-02-05)
|
|
13
|
+
|
|
14
|
+
|
|
15
|
+
### Bug Fixes
|
|
16
|
+
|
|
17
|
+
* fix contextual search, closes [#380](https://github.com/easyops-cn/docusaurus-search-local/issues/380) ([2a6d9d4](https://github.com/easyops-cn/docusaurus-search-local/commit/2a6d9d4f6ad7daea4f2c3c41604494a6a94492f3))
|
|
18
|
+
|
|
5
19
|
## [0.48.4](https://github.com/easyops-cn/docusaurus-search-local/compare/v0.48.3...v0.48.4) (2025-01-20)
|
|
6
20
|
|
|
7
21
|
|
|
@@ -70,8 +70,14 @@ export default function SearchBar({ handleSearchBarToggle, }) {
|
|
|
70
70
|
const search = useRef(null);
|
|
71
71
|
const prevSearchContext = useRef("");
|
|
72
72
|
const [searchContext, setSearchContext] = useState("");
|
|
73
|
+
const prevVersionUrl = useRef(baseUrl);
|
|
73
74
|
useEffect(() => {
|
|
74
75
|
if (!Array.isArray(searchContextByPaths)) {
|
|
76
|
+
if (prevVersionUrl.current !== versionUrl) {
|
|
77
|
+
// Reset index state map once version url is changed.
|
|
78
|
+
indexStateMap.current.delete("");
|
|
79
|
+
prevVersionUrl.current = versionUrl;
|
|
80
|
+
}
|
|
75
81
|
return;
|
|
76
82
|
}
|
|
77
83
|
let nextSearchContext = "";
|
|
@@ -2,9 +2,13 @@ export let language = ["en", "zh"];
|
|
|
2
2
|
export let removeDefaultStopWordFilter = false;
|
|
3
3
|
export const searchIndexUrl = "search-index{dir}.json?_=abc";
|
|
4
4
|
export const searchResultLimits = 8;
|
|
5
|
+
export let fuzzyMatchingDistance = 0;
|
|
5
6
|
export function __setLanguage(value) {
|
|
6
7
|
language = value;
|
|
7
8
|
}
|
|
8
9
|
export function __setRemoveDefaultStopWordFilter(value) {
|
|
9
10
|
removeDefaultStopWordFilter = value;
|
|
10
11
|
}
|
|
12
|
+
export function __setFuzzyMatchingDistance(value) {
|
|
13
|
+
fuzzyMatchingDistance = value;
|
|
14
|
+
}
|
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
import lunr from "lunr";
|
|
2
2
|
import { smartTerms } from "./smartTerms";
|
|
3
|
-
import { language, removeDefaultStopWordFilter } from "./proxiedGeneratedConstants";
|
|
3
|
+
import { language, removeDefaultStopWordFilter, fuzzyMatchingDistance, } from "./proxiedGeneratedConstants";
|
|
4
4
|
/**
|
|
5
5
|
* Get all possible queries for a list of tokens consists of words mixed English and Chinese,
|
|
6
6
|
* by a Chinese words dictionary.
|
|
@@ -76,28 +76,42 @@ export function smartQueries(tokens, zhDictionary) {
|
|
|
76
76
|
}
|
|
77
77
|
}
|
|
78
78
|
}
|
|
79
|
-
return getQueriesMaybeTyping(terms).concat(
|
|
79
|
+
return getQueriesMaybeTyping(terms).concat(fuzzyMatchingDistance > 0
|
|
80
|
+
? getQueriesMaybeTyping(terms, fuzzyMatchingDistance)
|
|
81
|
+
: [], getQueriesMaybeTyping(extraTerms), fuzzyMatchingDistance > 0
|
|
82
|
+
? getQueriesMaybeTyping(extraTerms, fuzzyMatchingDistance)
|
|
83
|
+
: []);
|
|
80
84
|
}
|
|
81
|
-
function getQueriesMaybeTyping(terms) {
|
|
82
|
-
return termsToQueries(terms).concat(termsToQueries(
|
|
85
|
+
function getQueriesMaybeTyping(terms, editDistance) {
|
|
86
|
+
return termsToQueries(terms, false, editDistance).concat(termsToQueries(
|
|
83
87
|
// Ignore terms whose last token already has a trailing wildcard,
|
|
84
88
|
// or the last token is not `maybeTyping`.
|
|
85
89
|
terms.filter((term) => {
|
|
86
90
|
const token = term[term.length - 1];
|
|
87
91
|
return !token.trailing && token.maybeTyping;
|
|
88
|
-
}), true));
|
|
92
|
+
}), true, editDistance));
|
|
89
93
|
}
|
|
90
|
-
function termsToQueries(terms, maybeTyping) {
|
|
91
|
-
return terms.
|
|
92
|
-
|
|
93
|
-
|
|
94
|
-
|
|
95
|
-
|
|
96
|
-
|
|
97
|
-
|
|
98
|
-
|
|
99
|
-
?
|
|
100
|
-
|
|
101
|
-
|
|
102
|
-
|
|
94
|
+
function termsToQueries(terms, maybeTyping, editDistance) {
|
|
95
|
+
return terms.flatMap((term) => {
|
|
96
|
+
const query = {
|
|
97
|
+
tokens: term.map((item) => item.value),
|
|
98
|
+
term: term.map((item) => ({
|
|
99
|
+
value: item.value,
|
|
100
|
+
presence: lunr.Query.presence.REQUIRED,
|
|
101
|
+
// The last token of a term maybe incomplete while user is typing.
|
|
102
|
+
// So append more queries with trailing wildcard added.
|
|
103
|
+
wildcard: (maybeTyping ? item.trailing || item.maybeTyping : item.trailing)
|
|
104
|
+
? lunr.Query.wildcard.TRAILING
|
|
105
|
+
: lunr.Query.wildcard.NONE,
|
|
106
|
+
editDistance: editDistance && item.value.length > editDistance
|
|
107
|
+
? editDistance
|
|
108
|
+
: undefined,
|
|
109
|
+
})),
|
|
110
|
+
};
|
|
111
|
+
// Ignore queries that all terms ignored edit distance due to too short tokens.
|
|
112
|
+
if (editDistance && query.term.every((item) => !item.editDistance)) {
|
|
113
|
+
return [];
|
|
114
|
+
}
|
|
115
|
+
return query;
|
|
116
|
+
});
|
|
103
117
|
}
|
|
@@ -6,7 +6,7 @@ const fs_1 = tslib_1.__importDefault(require("fs"));
|
|
|
6
6
|
const path_1 = tslib_1.__importDefault(require("path"));
|
|
7
7
|
const getIndexHash_1 = require("./getIndexHash");
|
|
8
8
|
function generate(config, dir) {
|
|
9
|
-
const { language, removeDefaultStopWordFilter, removeDefaultStemmer, highlightSearchTermsOnTargetPage, searchResultLimits, searchResultContextMaxLength, explicitSearchResultPath, searchBarShortcut, searchBarShortcutHint, searchBarPosition, docsPluginIdForPreferredVersion, indexDocs, searchContextByPaths, hideSearchBarWithNoSearchContext, useAllContextsWithNoSearchContext, } = config;
|
|
9
|
+
const { language, removeDefaultStopWordFilter, removeDefaultStemmer, highlightSearchTermsOnTargetPage, searchResultLimits, searchResultContextMaxLength, explicitSearchResultPath, searchBarShortcut, searchBarShortcutHint, searchBarPosition, docsPluginIdForPreferredVersion, indexDocs, searchContextByPaths, hideSearchBarWithNoSearchContext, useAllContextsWithNoSearchContext, fuzzyMatchingDistance, } = config;
|
|
10
10
|
const indexHash = (0, getIndexHash_1.getIndexHash)(config);
|
|
11
11
|
const contents = [];
|
|
12
12
|
contents.push(`export const removeDefaultStemmer = ${JSON.stringify(removeDefaultStemmer)};`);
|
|
@@ -62,7 +62,7 @@ function generate(config, dir) {
|
|
|
62
62
|
constantContents.push(`export const removeDefaultStopWordFilter = ${JSON.stringify(removeDefaultStopWordFilter)};`);
|
|
63
63
|
constantContents.push(`export const language = ${JSON.stringify(language)};`);
|
|
64
64
|
const searchIndexUrl = searchIndexFilename + searchIndexQuery;
|
|
65
|
-
constantContents.push(`export const searchIndexUrl = ${JSON.stringify(searchIndexUrl)};`, `export const searchResultLimits = ${JSON.stringify(searchResultLimits)};`);
|
|
65
|
+
constantContents.push(`export const searchIndexUrl = ${JSON.stringify(searchIndexUrl)};`, `export const searchResultLimits = ${JSON.stringify(searchResultLimits)};`, `export const fuzzyMatchingDistance = ${JSON.stringify(fuzzyMatchingDistance)};`);
|
|
66
66
|
fs_1.default.writeFileSync(path_1.default.join(dir, "generated-constants.js"), constantContents.join("\n"));
|
|
67
67
|
return searchIndexFilename;
|
|
68
68
|
}
|
|
@@ -36,6 +36,7 @@ const schema = utils_validation_1.Joi.object({
|
|
|
36
36
|
hideSearchBarWithNoSearchContext: utils_validation_1.Joi.boolean().default(false),
|
|
37
37
|
useAllContextsWithNoSearchContext: utils_validation_1.Joi.boolean().default(false),
|
|
38
38
|
forceIgnoreNoIndex: utils_validation_1.Joi.boolean().default(false),
|
|
39
|
+
fuzzyMatchingDistance: utils_validation_1.Joi.number().default(1),
|
|
39
40
|
});
|
|
40
41
|
function validateOptions({ options, validate, }) {
|
|
41
42
|
return validate(schema, options || {});
|
package/dist/types/index.d.ts
CHANGED
|
@@ -173,4 +173,11 @@ export interface PluginOptions {
|
|
|
173
173
|
* @default false
|
|
174
174
|
*/
|
|
175
175
|
forceIgnoreNoIndex?: boolean;
|
|
176
|
+
/**
|
|
177
|
+
* Set the edit distance for fuzzy matching during searches. Lower values will result in stricter matches,
|
|
178
|
+
* while higher values will allow for more lenient matches. Set 0 to disable fuzzy matching.
|
|
179
|
+
*
|
|
180
|
+
* @default 1
|
|
181
|
+
*/
|
|
182
|
+
fuzzyMatchingDistance?: number;
|
|
176
183
|
}
|