@openclaw/brave-plugin 2026.9.6 → 2026.9.8
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/assets/icon.png +0 -0
- package/dist/.setup/{brave-web-search-provider-DEK9TtrN.mjs → brave-web-search-provider-DJmw8wv_.mjs} +4 -7
- package/dist/.setup/{brave-web-search-provider.runtime-h1k4SAtG.mjs → brave-web-search-provider.runtime-B7NtRbBA.mjs} +10 -37
- package/dist/index.js +1 -1
- package/dist/web-search-contract-api.js +1 -1
- package/dist/web-search-provider.js +1 -1
- package/dist/web-search-shared.js +4 -16
- package/package.json +4 -4
package/assets/icon.png
CHANGED
|
Binary file
|
|
@@ -1,14 +1,14 @@
|
|
|
1
|
-
import { buildBraveWebSearchProviderBase } from "../web-search-shared.js";
|
|
1
|
+
import { buildBraveWebSearchProviderBase, resolveBraveMode } from "../web-search-shared.js";
|
|
2
2
|
import { isDiagnosticFlagEnabled } from "openclaw/plugin-sdk/diagnostic-flags";
|
|
3
3
|
import { createLazyRuntimeModule } from "openclaw/plugin-sdk/lazy-runtime";
|
|
4
4
|
import { mergeScopedSearchConfig, resolveProviderWebSearchPluginConfig } from "openclaw/plugin-sdk/provider-web-search-config-contract";
|
|
5
|
-
import {
|
|
5
|
+
import { asOptionalRecord } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
6
6
|
//#region extensions/brave/src/brave-web-search-provider.ts
|
|
7
7
|
/**
|
|
8
8
|
* Brave web-search provider factory. It builds the agent tool definition and
|
|
9
9
|
* lazy-loads HTTP execution only when a search is run.
|
|
10
10
|
*/
|
|
11
|
-
const loadBraveWebSearchRuntime = createLazyRuntimeModule(() => import("./brave-web-search-provider.runtime-
|
|
11
|
+
const loadBraveWebSearchRuntime = createLazyRuntimeModule(() => import("./brave-web-search-provider.runtime-B7NtRbBA.mjs"));
|
|
12
12
|
const BraveSearchSchema = {
|
|
13
13
|
type: "object",
|
|
14
14
|
properties: {
|
|
@@ -52,11 +52,8 @@ const BraveSearchSchema = {
|
|
|
52
52
|
}
|
|
53
53
|
}
|
|
54
54
|
};
|
|
55
|
-
function resolveBraveMode(searchConfig) {
|
|
56
|
-
return (isRecord(searchConfig?.brave) ? searchConfig.brave : void 0)?.mode === "llm-context" ? "llm-context" : "web";
|
|
57
|
-
}
|
|
58
55
|
function createBraveToolDefinition(searchConfig, config) {
|
|
59
|
-
const braveMode = resolveBraveMode(searchConfig);
|
|
56
|
+
const braveMode = resolveBraveMode(asOptionalRecord(searchConfig?.brave));
|
|
60
57
|
const diagnosticsEnabled = isDiagnosticFlagEnabled("brave.http", config);
|
|
61
58
|
return {
|
|
62
59
|
description: braveMode === "llm-context" ? "Search the web using Brave Search LLM Context API. Returns pre-extracted page content (text chunks, tables, code blocks) optimized for LLM grounding." : "Search the web using Brave Search API. Supports region-specific and localized search via country and language parameters. Returns titles, URLs, and snippets for fast research.",
|
|
@@ -1,4 +1,5 @@
|
|
|
1
|
-
import {
|
|
1
|
+
import { resolveBraveMode } from "../web-search-shared.js";
|
|
2
|
+
import { asNonArrayRecord, normalizeLowercaseStringOrEmpty, normalizeOptionalString } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
2
3
|
import { buildTimeoutAbortSignal } from "openclaw/plugin-sdk/extension-shared";
|
|
3
4
|
import { assertOkOrThrowProviderError, readProviderJsonResponse } from "openclaw/plugin-sdk/provider-http";
|
|
4
5
|
import { DEFAULT_SEARCH_COUNT, MAX_SEARCH_COUNT, buildSearchCacheKey, formatCliCommand, parseWebSearchTimeFilters, readCachedSearchPayload, readConfiguredSecretString, readPositiveIntegerParam, readProviderEnvValue, readStringParam, resolveSearchCacheTtlMs, resolveSearchCount, resolveSearchTimeoutSeconds, resolveSiteName, withSelfHostedWebToolsEndpoint, withTrustedWebToolsEndpoint, wrapWebContent, writeCachedSearchPayload } from "openclaw/plugin-sdk/provider-web-search";
|
|
@@ -112,41 +113,24 @@ const BRAVE_SEARCH_LANG_ALIASES = {
|
|
|
112
113
|
};
|
|
113
114
|
const BRAVE_UI_LANG_LOCALE = /^([a-z]{2})-([a-z]{2})$/i;
|
|
114
115
|
function normalizeBraveSearchLang(value) {
|
|
115
|
-
|
|
116
|
-
const trimmed = value.trim();
|
|
117
|
-
if (!trimmed) return;
|
|
118
|
-
const lower = normalizeLowercaseStringOrEmpty(trimmed);
|
|
116
|
+
const lower = normalizeLowercaseStringOrEmpty(value);
|
|
119
117
|
const canonical = BRAVE_SEARCH_LANG_ALIASES[lower] ?? lower;
|
|
120
|
-
|
|
121
|
-
return canonical;
|
|
118
|
+
return BRAVE_SEARCH_LANG_CODES.has(canonical) ? canonical : void 0;
|
|
122
119
|
}
|
|
123
120
|
/** Normalize Brave country filter values. */
|
|
124
121
|
function normalizeBraveCountry(value) {
|
|
125
|
-
|
|
126
|
-
const trimmed = value.trim();
|
|
122
|
+
const trimmed = normalizeOptionalString(value);
|
|
127
123
|
if (!trimmed) return;
|
|
128
124
|
const canonical = trimmed.toUpperCase();
|
|
129
125
|
return BRAVE_COUNTRY_CODES.has(canonical) ? canonical : "ALL";
|
|
130
126
|
}
|
|
131
127
|
function normalizeBraveUiLang(value) {
|
|
132
|
-
|
|
133
|
-
const trimmed = value.trim();
|
|
134
|
-
if (!trimmed) return;
|
|
135
|
-
const match = trimmed.match(BRAVE_UI_LANG_LOCALE);
|
|
128
|
+
const match = normalizeOptionalString(value)?.match(BRAVE_UI_LANG_LOCALE);
|
|
136
129
|
if (!match) return;
|
|
137
130
|
const [, language, region] = match;
|
|
138
131
|
if (!language || !region) return;
|
|
139
132
|
return `${normalizeLowercaseStringOrEmpty(language)}-${region.toUpperCase()}`;
|
|
140
133
|
}
|
|
141
|
-
/** Resolve Brave-specific web-search config from scoped search config. */
|
|
142
|
-
function resolveBraveConfig(searchConfig) {
|
|
143
|
-
const brave = searchConfig?.brave;
|
|
144
|
-
return brave && typeof brave === "object" && !Array.isArray(brave) ? brave : {};
|
|
145
|
-
}
|
|
146
|
-
/** Resolve whether Brave should use web search or LLM Context API mode. */
|
|
147
|
-
function resolveBraveMode(brave) {
|
|
148
|
-
return brave?.mode === "llm-context" ? "llm-context" : "web";
|
|
149
|
-
}
|
|
150
134
|
/** Normalize Brave search and UI language params, detecting swapped fields. */
|
|
151
135
|
function normalizeBraveLanguageParams(params) {
|
|
152
136
|
const rawSearchLang = normalizeOptionalString(params.search_lang);
|
|
@@ -313,7 +297,7 @@ async function runBraveWebSearch(params) {
|
|
|
313
297
|
if (params.ui_lang) url.searchParams.set("ui_lang", params.ui_lang);
|
|
314
298
|
}
|
|
315
299
|
}, "Brave Search API error");
|
|
316
|
-
return (Array.isArray(data.web?.results) ? data.web
|
|
300
|
+
return (Array.isArray(data.web?.results) ? data.web.results : []).slice(0, params.count).map((entry) => {
|
|
317
301
|
const description = entry.description ?? "";
|
|
318
302
|
const title = entry.title ?? "";
|
|
319
303
|
const url = entry.url ?? "";
|
|
@@ -330,7 +314,7 @@ async function runBraveWebSearch(params) {
|
|
|
330
314
|
async function executeBraveSearch(args, searchConfig, options) {
|
|
331
315
|
const apiKey = resolveBraveApiKey(searchConfig);
|
|
332
316
|
if (!apiKey) return missingBraveKeyPayload();
|
|
333
|
-
const braveConfig =
|
|
317
|
+
const braveConfig = asNonArrayRecord(searchConfig?.brave);
|
|
334
318
|
const braveMode = resolveBraveMode(braveConfig);
|
|
335
319
|
const braveBaseUrl = resolveBraveBaseUrl(braveConfig);
|
|
336
320
|
const { signal, cleanup } = buildTimeoutAbortSignal({
|
|
@@ -401,7 +385,7 @@ async function executeBraveSearch(args, searchConfig, options) {
|
|
|
401
385
|
}
|
|
402
386
|
const llmContextDateEnd = braveMode === "llm-context" && dateAfter ? dateBefore ?? (/* @__PURE__ */ new Date()).toISOString().slice(0, 10) : dateBefore;
|
|
403
387
|
const requestedCount = resolveSearchCount(count, DEFAULT_SEARCH_COUNT);
|
|
404
|
-
const cacheKey = buildSearchCacheKey(
|
|
388
|
+
const cacheKey = buildSearchCacheKey([
|
|
405
389
|
"brave",
|
|
406
390
|
braveMode,
|
|
407
391
|
braveBaseUrl,
|
|
@@ -409,21 +393,10 @@ async function executeBraveSearch(args, searchConfig, options) {
|
|
|
409
393
|
requestedCount,
|
|
410
394
|
country,
|
|
411
395
|
normalizedLanguage.search_lang,
|
|
396
|
+
...braveMode === "web" ? [normalizedLanguage.ui_lang] : [],
|
|
412
397
|
freshness,
|
|
413
398
|
dateAfter,
|
|
414
399
|
llmContextDateEnd
|
|
415
|
-
] : [
|
|
416
|
-
"brave",
|
|
417
|
-
braveMode,
|
|
418
|
-
braveBaseUrl,
|
|
419
|
-
query,
|
|
420
|
-
requestedCount,
|
|
421
|
-
country,
|
|
422
|
-
normalizedLanguage.search_lang,
|
|
423
|
-
normalizedLanguage.ui_lang,
|
|
424
|
-
freshness,
|
|
425
|
-
dateAfter,
|
|
426
|
-
dateBefore
|
|
427
400
|
]);
|
|
428
401
|
const diagnostics = { enabled: options?.diagnosticsEnabled === true };
|
|
429
402
|
const cacheTtlMs = resolveSearchCacheTtlMs(searchConfig);
|
package/dist/index.js
CHANGED
|
@@ -1,4 +1,4 @@
|
|
|
1
|
-
import { t as createBraveWebSearchProvider } from "./.setup/brave-web-search-provider-
|
|
1
|
+
import { t as createBraveWebSearchProvider } from "./.setup/brave-web-search-provider-DJmw8wv_.mjs";
|
|
2
2
|
import { definePluginEntry } from "openclaw/plugin-sdk/plugin-entry";
|
|
3
3
|
//#region extensions/brave/index.ts
|
|
4
4
|
/**
|
|
@@ -1,3 +1,3 @@
|
|
|
1
|
-
import { t as createBraveWebSearchProvider } from "./.setup/brave-web-search-provider-
|
|
1
|
+
import { t as createBraveWebSearchProvider } from "./.setup/brave-web-search-provider-DJmw8wv_.mjs";
|
|
2
2
|
import "./web-search-provider.js";
|
|
3
3
|
export { createBraveWebSearchProvider };
|
|
@@ -1,2 +1,2 @@
|
|
|
1
|
-
import { t as createBraveWebSearchProvider } from "./.setup/brave-web-search-provider-
|
|
1
|
+
import { t as createBraveWebSearchProvider } from "./.setup/brave-web-search-provider-DJmw8wv_.mjs";
|
|
2
2
|
export { createBraveWebSearchProvider };
|
|
@@ -1,23 +1,12 @@
|
|
|
1
1
|
import { createWebSearchProviderContractFields } from "openclaw/plugin-sdk/provider-web-search-config-contract";
|
|
2
|
-
import { isRecord } from "openclaw/plugin-sdk/string-coerce-runtime";
|
|
3
2
|
//#region extensions/brave/web-search-shared.ts
|
|
4
3
|
/**
|
|
5
4
|
* Shared Brave Search provider metadata and credential lookup. Contract tests
|
|
6
5
|
* and runtime provider creation both use this lightweight descriptor.
|
|
7
6
|
*/
|
|
8
|
-
/** Canonical config path for the Brave Search API key. */
|
|
9
7
|
const BRAVE_CREDENTIAL_PATH = "plugins.entries.brave.config.webSearch.apiKey";
|
|
10
|
-
function
|
|
11
|
-
|
|
12
|
-
const plugins = isRecord(config.plugins) ? config.plugins : void 0;
|
|
13
|
-
const entries = isRecord(plugins?.entries) ? plugins.entries : void 0;
|
|
14
|
-
const entry = isRecord(entries?.brave) ? entries.brave : void 0;
|
|
15
|
-
const pluginConfig = isRecord(entry?.config) ? entry.config : void 0;
|
|
16
|
-
return isRecord(pluginConfig?.webSearch) ? pluginConfig.webSearch : void 0;
|
|
17
|
-
}
|
|
18
|
-
/** Resolve Brave credentials from current plugin config. */
|
|
19
|
-
function resolveConfiguredBraveCredential(config) {
|
|
20
|
-
return resolveBraveWebSearchPluginConfig(config)?.apiKey;
|
|
8
|
+
function resolveBraveMode(brave) {
|
|
9
|
+
return brave?.mode === "llm-context" ? "llm-context" : "web";
|
|
21
10
|
}
|
|
22
11
|
/** Build the common Brave provider metadata without the runtime tool executor. */
|
|
23
12
|
function buildBraveWebSearchProviderBase() {
|
|
@@ -37,9 +26,8 @@ function buildBraveWebSearchProviderBase() {
|
|
|
37
26
|
credentialPath: BRAVE_CREDENTIAL_PATH,
|
|
38
27
|
searchCredential: { type: "top-level" },
|
|
39
28
|
configuredCredential: { pluginId: "brave" }
|
|
40
|
-
})
|
|
41
|
-
getConfiguredCredentialValue: resolveConfiguredBraveCredential
|
|
29
|
+
})
|
|
42
30
|
};
|
|
43
31
|
}
|
|
44
32
|
//#endregion
|
|
45
|
-
export { buildBraveWebSearchProviderBase };
|
|
33
|
+
export { buildBraveWebSearchProviderBase, resolveBraveMode };
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "@openclaw/brave-plugin",
|
|
3
|
-
"version": "2026.9.
|
|
3
|
+
"version": "2026.9.8",
|
|
4
4
|
"description": "OpenClaw Brave Search provider plugin for web search.",
|
|
5
5
|
"repository": {
|
|
6
6
|
"type": "git",
|
|
@@ -19,10 +19,10 @@
|
|
|
19
19
|
"allowInvalidConfigRecovery": true
|
|
20
20
|
},
|
|
21
21
|
"compat": {
|
|
22
|
-
"pluginApi": ">=2026.9.
|
|
22
|
+
"pluginApi": ">=2026.9.8"
|
|
23
23
|
},
|
|
24
24
|
"build": {
|
|
25
|
-
"openclawVersion": "2026.9.
|
|
25
|
+
"openclawVersion": "2026.9.8"
|
|
26
26
|
},
|
|
27
27
|
"release": {
|
|
28
28
|
"publishToClawHub": true,
|
|
@@ -40,7 +40,7 @@
|
|
|
40
40
|
"assets/activity.svg"
|
|
41
41
|
],
|
|
42
42
|
"peerDependencies": {
|
|
43
|
-
"openclaw": ">=2026.9.
|
|
43
|
+
"openclaw": ">=2026.9.8"
|
|
44
44
|
},
|
|
45
45
|
"peerDependenciesMeta": {
|
|
46
46
|
"openclaw": {
|