dsh-web-search-enhanced 0.2.0 → 0.2.1
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/README.md +19 -2
- package/lib/client.cjs +721 -538
- package/lib/client.cjs.map +1 -1
- package/lib/index.js +1323 -281
- package/package.json +3 -1
package/lib/client.cjs
CHANGED
|
@@ -33,7 +33,11 @@ window.__ModuleLoader__.load({
|
|
|
33
33
|
const SEARCH = {
|
|
34
34
|
packageName: "dsh-web-search-enhanced",
|
|
35
35
|
rowId: "web-search-enhanced",
|
|
36
|
-
providerId: "search-enhanced"
|
|
36
|
+
providerId: "search-enhanced",
|
|
37
|
+
tools: {
|
|
38
|
+
action: "web_search_enhanced",
|
|
39
|
+
list: "list_web_search_providers"
|
|
40
|
+
}
|
|
37
41
|
};
|
|
38
42
|
/**
|
|
39
43
|
* Key of a row's configuration page on the Plugins page (`plugins.row.config`).
|
|
@@ -151,6 +155,7 @@ window.__ModuleLoader__.load({
|
|
|
151
155
|
"version",
|
|
152
156
|
"defaultConnection",
|
|
153
157
|
"showSelector",
|
|
158
|
+
"enhancedTools",
|
|
154
159
|
"defaults",
|
|
155
160
|
"connections"
|
|
156
161
|
];
|
|
@@ -193,8 +198,16 @@ window.__ModuleLoader__.load({
|
|
|
193
198
|
}
|
|
194
199
|
return result;
|
|
195
200
|
}
|
|
201
|
+
/**
|
|
202
|
+
* Operator text shown as one line (a label in menus, error messages and the
|
|
203
|
+
* Agent's provider list): control characters and line or paragraph separators
|
|
204
|
+
* become spaces, runs of whitespace one space, the ends trimmed.
|
|
205
|
+
*/
|
|
206
|
+
function singleLine(value) {
|
|
207
|
+
return value.replaceAll(/[\p{Cc}\p{Zl}\p{Zp}]/gu, " ").replaceAll(/\s+/gu, " ").trim();
|
|
208
|
+
}
|
|
196
209
|
const text = zod.z.string().trim().min(1).max(TEXT_MAX_LENGTH);
|
|
197
|
-
const label = zod.z.string().
|
|
210
|
+
const label = zod.z.string().transform(singleLine).pipe(zod.z.string().min(1).max(200));
|
|
198
211
|
const credentialRef = text.regex(CREDENTIAL_REF, "must be a credential reference such as EXA_API_KEY");
|
|
199
212
|
const endpoint = text.refine(isEndpoint, "must be an absolute http(s) URL without credentials, query or fragment");
|
|
200
213
|
const options = zod.z.record(zod.z.string(), zod.z.unknown());
|
|
@@ -203,6 +216,7 @@ window.__ModuleLoader__.load({
|
|
|
203
216
|
version: zod.z.literal(currentVersion).optional(),
|
|
204
217
|
defaultConnection: zod.z.string().min(1).max(200).optional(),
|
|
205
218
|
showSelector: zod.z.boolean().optional(),
|
|
219
|
+
enhancedTools: zod.z.boolean().optional(),
|
|
206
220
|
defaults: defaults.optional(),
|
|
207
221
|
connections: zod.z.record(zod.z.string().max(200), zod.z.unknown()).refine((value) => Object.keys(value).length <= 200, "must contain at most 200 connections").optional()
|
|
208
222
|
});
|
|
@@ -264,7 +278,7 @@ window.__ModuleLoader__.load({
|
|
|
264
278
|
const customSchema = customConnectionSchema(adapterKeys, protocolKeys);
|
|
265
279
|
const connections = /* @__PURE__ */ new Map();
|
|
266
280
|
const rejectId = (id, path) => fail(path, "unknown connection id \"" + id + "\"; this release does not read 0.1.x settings; remove the field or use Reset on the settings page");
|
|
267
|
-
const resolve = (id, key, override,
|
|
281
|
+
const resolve = (id, key, override, origin) => {
|
|
268
282
|
const info = catalog[key];
|
|
269
283
|
const path = "connections." + id;
|
|
270
284
|
const access = info.kind === "model" ? "api-key" : override.access ?? defaultAccess(info.access);
|
|
@@ -276,11 +290,12 @@ window.__ModuleLoader__.load({
|
|
|
276
290
|
if (problems.length > 0) fail(path + ".options", problems.join("; ") + "; this release does not read 0.1.x settings; remove the field or use Reset on the settings page");
|
|
277
291
|
const trustedEndpoint = override.trustedEndpoint ?? false;
|
|
278
292
|
for (const [name, rule] of Object.entries(info.options)) if (rule.kind === "url" && values[name] !== void 0 && values[name] !== info.endpoint && !trustedEndpoint) fail(path + ".trustedEndpoint", "a non-official " + name + " needs trustedEndpoint: true");
|
|
293
|
+
const disabled = override.disabled ?? (origin.kind === "builtin" ? info.optIn : false);
|
|
279
294
|
const base = {
|
|
280
295
|
id,
|
|
281
296
|
catalogKey: key,
|
|
282
297
|
label: override.label ?? info.label,
|
|
283
|
-
disabled
|
|
298
|
+
disabled,
|
|
284
299
|
remote: info.remote,
|
|
285
300
|
trustedEndpoint,
|
|
286
301
|
options: values
|
|
@@ -297,7 +312,7 @@ window.__ModuleLoader__.load({
|
|
|
297
312
|
};
|
|
298
313
|
if (info.kind !== "native" && info.kind !== "adapter") return fail(path + ".kind", "unsupported catalog kind");
|
|
299
314
|
if (!info.access.apiKey || info.endpoint === void 0) return fail(path, "remote catalog entry needs credentials and an endpoint");
|
|
300
|
-
const url =
|
|
315
|
+
const url = origin.kind === "custom" && origin.endpoint !== void 0 ? origin.endpoint : info.endpoint;
|
|
301
316
|
if (url !== info.endpoint && !trustedEndpoint) fail(path + ".trustedEndpoint", "a custom endpoint needs trustedEndpoint: true");
|
|
302
317
|
return {
|
|
303
318
|
...base,
|
|
@@ -318,7 +333,7 @@ window.__ModuleLoader__.load({
|
|
|
318
333
|
]) if (Object.hasOwn(raw, field)) fail("connections." + id + "." + field, "this connection takes its route from the Session model");
|
|
319
334
|
}
|
|
320
335
|
const override = raw === void 0 ? {} : parse(builtinOverrideSchema, raw, "connections." + id);
|
|
321
|
-
connections.set(id, resolve(id, key, override));
|
|
336
|
+
connections.set(id, resolve(id, key, override, { kind: "builtin" }));
|
|
322
337
|
}
|
|
323
338
|
for (const [id, raw] of Object.entries(overrides)) {
|
|
324
339
|
if (connections.has(id)) continue;
|
|
@@ -328,7 +343,10 @@ window.__ModuleLoader__.load({
|
|
|
328
343
|
if (custom.kind === "adapter") connections.set(id, resolve(id, custom.adapter, {
|
|
329
344
|
...custom,
|
|
330
345
|
access: "api-key"
|
|
331
|
-
},
|
|
346
|
+
}, {
|
|
347
|
+
kind: "custom",
|
|
348
|
+
endpoint: custom.endpoint
|
|
349
|
+
}));
|
|
332
350
|
else {
|
|
333
351
|
const info = protocols[custom.protocol];
|
|
334
352
|
const values = custom.options ?? {};
|
|
@@ -359,6 +377,7 @@ window.__ModuleLoader__.load({
|
|
|
359
377
|
version: migrations.currentVersion,
|
|
360
378
|
defaultConnection,
|
|
361
379
|
showSelector: settings.showSelector ?? true,
|
|
380
|
+
enhancedTools: settings.enhancedTools ?? false,
|
|
362
381
|
defaults: settings.defaults ?? parse(defaults.schema, {}, "defaults"),
|
|
363
382
|
connections
|
|
364
383
|
};
|
|
@@ -800,6 +819,7 @@ window.__ModuleLoader__.load({
|
|
|
800
819
|
const MODEL_PROTOCOLS = {
|
|
801
820
|
"anthropic-messages": {
|
|
802
821
|
label: "Anthropic Messages",
|
|
822
|
+
use: "the model searches and answers",
|
|
803
823
|
options: {
|
|
804
824
|
maxTokens,
|
|
805
825
|
anthropicTool,
|
|
@@ -815,6 +835,7 @@ window.__ModuleLoader__.load({
|
|
|
815
835
|
},
|
|
816
836
|
"openai-responses": {
|
|
817
837
|
label: "OpenAI Responses",
|
|
838
|
+
use: "the model searches and answers",
|
|
818
839
|
options: {
|
|
819
840
|
maxTokens,
|
|
820
841
|
responsesTool,
|
|
@@ -828,6 +849,7 @@ window.__ModuleLoader__.load({
|
|
|
828
849
|
},
|
|
829
850
|
"openai-chat-completions": {
|
|
830
851
|
label: "OpenAI Chat Completions",
|
|
852
|
+
use: "the model searches and answers",
|
|
831
853
|
options: {
|
|
832
854
|
maxTokens,
|
|
833
855
|
searchContextSize,
|
|
@@ -847,6 +869,8 @@ window.__ModuleLoader__.load({
|
|
|
847
869
|
label: "DeepSeek Messages",
|
|
848
870
|
kind: "native",
|
|
849
871
|
remote: true,
|
|
872
|
+
optIn: false,
|
|
873
|
+
use: "answers with a summary and sources",
|
|
850
874
|
endpoint: "https://api.deepseek.com/anthropic/v1",
|
|
851
875
|
homepage: "https://platform.deepseek.com",
|
|
852
876
|
access: nativeAccess,
|
|
@@ -877,6 +901,7 @@ window.__ModuleLoader__.load({
|
|
|
877
901
|
label: "DeepSeek Search API",
|
|
878
902
|
kind: "native",
|
|
879
903
|
remote: true,
|
|
904
|
+
optIn: true,
|
|
880
905
|
endpoint: "https://api.deepseek.com/v1/tools",
|
|
881
906
|
homepage: "https://platform.deepseek.com",
|
|
882
907
|
access: nativeAccess,
|
|
@@ -895,6 +920,8 @@ window.__ModuleLoader__.load({
|
|
|
895
920
|
label: "Session model",
|
|
896
921
|
kind: "model",
|
|
897
922
|
remote: true,
|
|
923
|
+
optIn: false,
|
|
924
|
+
use: "the session model searches and answers",
|
|
898
925
|
access: {
|
|
899
926
|
keyless: false,
|
|
900
927
|
apiKey: false,
|
|
@@ -914,6 +941,7 @@ window.__ModuleLoader__.load({
|
|
|
914
941
|
},
|
|
915
942
|
kind: "adapter",
|
|
916
943
|
remote: true,
|
|
944
|
+
optIn: true,
|
|
917
945
|
freshness: ["api-key"],
|
|
918
946
|
homepage: "https://exa.ai",
|
|
919
947
|
options: { type: {
|
|
@@ -936,6 +964,7 @@ window.__ModuleLoader__.load({
|
|
|
936
964
|
},
|
|
937
965
|
kind: "adapter",
|
|
938
966
|
remote: true,
|
|
967
|
+
optIn: true,
|
|
939
968
|
freshness: ["keyless", "api-key"],
|
|
940
969
|
homepage: "https://www.firecrawl.dev",
|
|
941
970
|
options: {
|
|
@@ -961,6 +990,7 @@ window.__ModuleLoader__.load({
|
|
|
961
990
|
},
|
|
962
991
|
kind: "adapter",
|
|
963
992
|
remote: true,
|
|
993
|
+
optIn: true,
|
|
964
994
|
freshness: [],
|
|
965
995
|
homepage: "https://www.tavily.com",
|
|
966
996
|
options: {
|
|
@@ -993,6 +1023,7 @@ window.__ModuleLoader__.load({
|
|
|
993
1023
|
},
|
|
994
1024
|
kind: "adapter",
|
|
995
1025
|
remote: true,
|
|
1026
|
+
optIn: true,
|
|
996
1027
|
freshness: [],
|
|
997
1028
|
homepage: "https://www.tinyfish.ai",
|
|
998
1029
|
options: {
|
|
@@ -1029,8 +1060,10 @@ window.__ModuleLoader__.load({
|
|
|
1029
1060
|
},
|
|
1030
1061
|
kind: "adapter",
|
|
1031
1062
|
remote: true,
|
|
1063
|
+
optIn: true,
|
|
1032
1064
|
freshness: [],
|
|
1033
1065
|
homepage: "https://openalex.org",
|
|
1066
|
+
use: "scholarly works (papers, citations); keyword queries",
|
|
1034
1067
|
options: {
|
|
1035
1068
|
sort: {
|
|
1036
1069
|
kind: "text",
|
|
@@ -1059,8 +1092,10 @@ window.__ModuleLoader__.load({
|
|
|
1059
1092
|
},
|
|
1060
1093
|
kind: "adapter",
|
|
1061
1094
|
remote: true,
|
|
1095
|
+
optIn: true,
|
|
1062
1096
|
freshness: [],
|
|
1063
1097
|
homepage: "https://www.semanticscholar.org/product/api",
|
|
1098
|
+
use: "academic papers (citations, TL;DR); keyword queries",
|
|
1064
1099
|
options: {
|
|
1065
1100
|
year: {
|
|
1066
1101
|
kind: "text",
|
|
@@ -1106,6 +1141,378 @@ window.__ModuleLoader__.load({
|
|
|
1106
1141
|
return (0, react.useSyncExternalStore)(subscribe, getSnapshot);
|
|
1107
1142
|
}
|
|
1108
1143
|
//#endregion
|
|
1144
|
+
//#region ../core/src/client/settings/parts.tsx
|
|
1145
|
+
/** Building blocks shared by the settings sections. */
|
|
1146
|
+
function classNames(...args) {
|
|
1147
|
+
return args.flat(Number.POSITIVE_INFINITY).filter(Boolean).map((arg) => {
|
|
1148
|
+
if (typeof arg === "string") return arg;
|
|
1149
|
+
if (typeof arg === "object" && arg !== null) return Object.entries(arg).filter(([, v]) => Boolean(v)).map(([k]) => k).join(" ");
|
|
1150
|
+
return "";
|
|
1151
|
+
}).filter(Boolean).join(" ");
|
|
1152
|
+
}
|
|
1153
|
+
/** A local schema failure whose diagnostic stays out of the translated message. */
|
|
1154
|
+
var SettingsValidationError = class extends Error {};
|
|
1155
|
+
function createSettingsParts({ classes: css, keys }) {
|
|
1156
|
+
/** `titleId` lets a control inside name itself by the section title. */
|
|
1157
|
+
function Section({ title, titleId, actions, children }) {
|
|
1158
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("section", {
|
|
1159
|
+
className: css.section,
|
|
1160
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1161
|
+
className: css.sectionHead,
|
|
1162
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("h4", {
|
|
1163
|
+
id: titleId,
|
|
1164
|
+
className: css.sectionTitle,
|
|
1165
|
+
children: title
|
|
1166
|
+
}), actions]
|
|
1167
|
+
}), children]
|
|
1168
|
+
});
|
|
1169
|
+
}
|
|
1170
|
+
/** Title and hint on the left, one control on the right; wraps under the text on narrow pages. */
|
|
1171
|
+
function SettingRow({ title, hint, children }) {
|
|
1172
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1173
|
+
className: css.settingRow,
|
|
1174
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1175
|
+
className: css.settingText,
|
|
1176
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
1177
|
+
className: css.settingTitle,
|
|
1178
|
+
children: title
|
|
1179
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
1180
|
+
className: css.hint,
|
|
1181
|
+
children: hint
|
|
1182
|
+
})]
|
|
1183
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
1184
|
+
className: css.settingControl,
|
|
1185
|
+
children
|
|
1186
|
+
})]
|
|
1187
|
+
});
|
|
1188
|
+
}
|
|
1189
|
+
/** A dropdown in the settings pill style, built on the shared Menu. */
|
|
1190
|
+
function SelectMenu({ label, title, value, options, disabled, onChange, compact = false }) {
|
|
1191
|
+
const [open, setOpen] = (0, react.useState)(false);
|
|
1192
|
+
const current = options.find((option) => option.id === value);
|
|
1193
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.Menu, {
|
|
1194
|
+
open,
|
|
1195
|
+
onClose: () => {
|
|
1196
|
+
setOpen(false);
|
|
1197
|
+
},
|
|
1198
|
+
items: options.map((option) => ({
|
|
1199
|
+
id: option.id,
|
|
1200
|
+
label: option.label
|
|
1201
|
+
})),
|
|
1202
|
+
selectedId: value,
|
|
1203
|
+
onSelect: (id) => {
|
|
1204
|
+
setOpen(false);
|
|
1205
|
+
if (id !== value) onChange(id);
|
|
1206
|
+
},
|
|
1207
|
+
align: "end",
|
|
1208
|
+
portal: true,
|
|
1209
|
+
anchor: /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("button", {
|
|
1210
|
+
type: "button",
|
|
1211
|
+
className: compact ? css.selectCompact : css.select,
|
|
1212
|
+
"aria-label": label,
|
|
1213
|
+
title,
|
|
1214
|
+
"aria-haspopup": "menu",
|
|
1215
|
+
"aria-expanded": open,
|
|
1216
|
+
disabled,
|
|
1217
|
+
onClick: () => {
|
|
1218
|
+
setOpen(!open);
|
|
1219
|
+
},
|
|
1220
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
1221
|
+
className: css.selectValue,
|
|
1222
|
+
children: current?.label ?? value
|
|
1223
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.IconChevronDownOutlineRegular, { className: css.selectChevron })]
|
|
1224
|
+
})
|
|
1225
|
+
});
|
|
1226
|
+
}
|
|
1227
|
+
/** Pending state and the last failure of one section's writes. */
|
|
1228
|
+
function useWrite(t) {
|
|
1229
|
+
const [state, setState] = (0, react.useState)({
|
|
1230
|
+
busy: false,
|
|
1231
|
+
error: void 0,
|
|
1232
|
+
errorTitle: void 0
|
|
1233
|
+
});
|
|
1234
|
+
const run = async (work) => {
|
|
1235
|
+
setState({
|
|
1236
|
+
busy: true,
|
|
1237
|
+
error: void 0,
|
|
1238
|
+
errorTitle: void 0
|
|
1239
|
+
});
|
|
1240
|
+
try {
|
|
1241
|
+
const accepted = await work();
|
|
1242
|
+
setState({
|
|
1243
|
+
busy: false,
|
|
1244
|
+
error: accepted ? void 0 : t(keys.refused),
|
|
1245
|
+
errorTitle: void 0
|
|
1246
|
+
});
|
|
1247
|
+
return accepted;
|
|
1248
|
+
} catch (error) {
|
|
1249
|
+
const message = error instanceof Error ? error.message : String(error);
|
|
1250
|
+
const invalid = error instanceof SettingsValidationError;
|
|
1251
|
+
setState({
|
|
1252
|
+
busy: false,
|
|
1253
|
+
error: invalid ? t(keys.invalid) : message || t(keys.failed),
|
|
1254
|
+
errorTitle: invalid ? message : void 0
|
|
1255
|
+
});
|
|
1256
|
+
return false;
|
|
1257
|
+
}
|
|
1258
|
+
};
|
|
1259
|
+
return {
|
|
1260
|
+
...state,
|
|
1261
|
+
run
|
|
1262
|
+
};
|
|
1263
|
+
}
|
|
1264
|
+
function ErrorText({ children, title }) {
|
|
1265
|
+
return children === void 0 ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
1266
|
+
className: css.error,
|
|
1267
|
+
role: "alert",
|
|
1268
|
+
title,
|
|
1269
|
+
children
|
|
1270
|
+
});
|
|
1271
|
+
}
|
|
1272
|
+
/** Inline confirmation of a destructive action: the question beside cancel and confirm. */
|
|
1273
|
+
function ConfirmRow({ message, confirmLabel, cancelLabel, disabled, onConfirm, onCancel }) {
|
|
1274
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1275
|
+
className: css.confirmRow,
|
|
1276
|
+
role: "group",
|
|
1277
|
+
"aria-label": message,
|
|
1278
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
1279
|
+
className: css.confirmText,
|
|
1280
|
+
children: message
|
|
1281
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1282
|
+
className: css.actions,
|
|
1283
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.Button, {
|
|
1284
|
+
variant: "ghost",
|
|
1285
|
+
size: "sm",
|
|
1286
|
+
onClick: onCancel,
|
|
1287
|
+
children: cancelLabel
|
|
1288
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.Button, {
|
|
1289
|
+
variant: "outline",
|
|
1290
|
+
size: "sm",
|
|
1291
|
+
className: css.danger,
|
|
1292
|
+
disabled,
|
|
1293
|
+
onClick: onConfirm,
|
|
1294
|
+
children: confirmLabel
|
|
1295
|
+
})]
|
|
1296
|
+
})]
|
|
1297
|
+
});
|
|
1298
|
+
}
|
|
1299
|
+
return {
|
|
1300
|
+
Section,
|
|
1301
|
+
SettingRow,
|
|
1302
|
+
SelectMenu,
|
|
1303
|
+
ErrorText,
|
|
1304
|
+
ConfirmRow,
|
|
1305
|
+
useWrite
|
|
1306
|
+
};
|
|
1307
|
+
}
|
|
1308
|
+
function applyOps(user, ops) {
|
|
1309
|
+
const root = structuredClone(user !== null && typeof user === "object" && !Array.isArray(user) ? user : {});
|
|
1310
|
+
for (const op of ops) {
|
|
1311
|
+
if (op.path.length === 0) continue;
|
|
1312
|
+
if (op.op === "set") {
|
|
1313
|
+
let current = root;
|
|
1314
|
+
for (let i = 0; i < op.path.length - 1; i++) {
|
|
1315
|
+
const seg = op.path[i];
|
|
1316
|
+
if (current[seg] === null || typeof current[seg] !== "object" || Array.isArray(current[seg])) current[seg] = {};
|
|
1317
|
+
current = current[seg];
|
|
1318
|
+
}
|
|
1319
|
+
current[op.path.at(-1)] = structuredClone(op.value);
|
|
1320
|
+
} else if (op.op === "unset") {
|
|
1321
|
+
let current = root;
|
|
1322
|
+
for (let i = 0; i < op.path.length - 1; i++) {
|
|
1323
|
+
const seg = op.path[i];
|
|
1324
|
+
if (current[seg] === null || typeof current[seg] !== "object" || Array.isArray(current[seg])) break;
|
|
1325
|
+
current = current[seg];
|
|
1326
|
+
}
|
|
1327
|
+
delete current[op.path.at(-1)];
|
|
1328
|
+
}
|
|
1329
|
+
}
|
|
1330
|
+
return root;
|
|
1331
|
+
}
|
|
1332
|
+
//#endregion
|
|
1333
|
+
//#region ../core/src/client/settings/document.ts
|
|
1334
|
+
/** ConfigForm.value is schema-projected; the raw layers retain unknown fields for validation. */
|
|
1335
|
+
function effectiveDocument(snapshot) {
|
|
1336
|
+
return merge(snapshot.base, snapshot.user);
|
|
1337
|
+
}
|
|
1338
|
+
/** Validate before exposing normal editors; only successful older migrations need writeback. */
|
|
1339
|
+
function editableSettings(raw, layers, writable, resolve, migrations = SETTINGS_MIGRATIONS) {
|
|
1340
|
+
try {
|
|
1341
|
+
const version = documentVersion$2(raw, migrations.currentVersion);
|
|
1342
|
+
const config = migrateDocument(raw, migrations);
|
|
1343
|
+
resolve(config);
|
|
1344
|
+
return {
|
|
1345
|
+
kind: "ready",
|
|
1346
|
+
config,
|
|
1347
|
+
layers,
|
|
1348
|
+
needsWriteback: writable && version.kind === "older"
|
|
1349
|
+
};
|
|
1350
|
+
} catch (error) {
|
|
1351
|
+
return {
|
|
1352
|
+
kind: "invalid",
|
|
1353
|
+
diagnostic: diagnostic(error),
|
|
1354
|
+
layers,
|
|
1355
|
+
needsWriteback: false
|
|
1356
|
+
};
|
|
1357
|
+
}
|
|
1358
|
+
}
|
|
1359
|
+
/** Check the exact recursively overlaid candidate that the settings store will persist. */
|
|
1360
|
+
function settingsOperations(layers, operations, resolve) {
|
|
1361
|
+
try {
|
|
1362
|
+
const candidate = effectiveDocument({
|
|
1363
|
+
base: layers.base,
|
|
1364
|
+
user: applyOps(layers.user, operations)
|
|
1365
|
+
});
|
|
1366
|
+
const result = [...operations];
|
|
1367
|
+
if (result.some((op) => op.op === "set") && candidate.version === void 0) {
|
|
1368
|
+
result.push({
|
|
1369
|
+
op: "set",
|
|
1370
|
+
path: ["version"],
|
|
1371
|
+
value: 2
|
|
1372
|
+
});
|
|
1373
|
+
candidate.version = 2;
|
|
1374
|
+
}
|
|
1375
|
+
resolve(candidate);
|
|
1376
|
+
return result;
|
|
1377
|
+
} catch (error) {
|
|
1378
|
+
throw new SettingsValidationError(diagnostic(error));
|
|
1379
|
+
}
|
|
1380
|
+
}
|
|
1381
|
+
/**
|
|
1382
|
+
* Share validation, revision fencing and automatic future migrations between both pages.
|
|
1383
|
+
* @param snapshot - the settings snapshot the page renders.
|
|
1384
|
+
* @param read - the settings snapshot now, which a write the form accepted has already updated.
|
|
1385
|
+
*/
|
|
1386
|
+
function useSettingsDocument(snapshot, read, resolve, mutate, migrations = SETTINGS_MIGRATIONS) {
|
|
1387
|
+
const view = (0, react.useMemo)(() => {
|
|
1388
|
+
if (snapshot.status === "unavailable" || snapshot.value === void 0 || snapshot.revision === void 0) return void 0;
|
|
1389
|
+
const result = editableSettings(effectiveDocument(snapshot), {
|
|
1390
|
+
base: snapshot.base,
|
|
1391
|
+
user: snapshot.user
|
|
1392
|
+
}, snapshot.writable, resolve, migrations);
|
|
1393
|
+
if (snapshot.diagnostic === void 0) return result;
|
|
1394
|
+
return {
|
|
1395
|
+
kind: "invalid",
|
|
1396
|
+
layers: result.layers,
|
|
1397
|
+
needsWriteback: false,
|
|
1398
|
+
diagnostic: result.kind === "invalid" ? result.diagnostic + "; " + snapshot.diagnostic : snapshot.diagnostic
|
|
1399
|
+
};
|
|
1400
|
+
}, [
|
|
1401
|
+
snapshot,
|
|
1402
|
+
resolve,
|
|
1403
|
+
migrations
|
|
1404
|
+
]);
|
|
1405
|
+
const attemptedRevision = (0, react.useRef)(void 0);
|
|
1406
|
+
const [failure, setFailure] = (0, react.useState)();
|
|
1407
|
+
const revision = snapshot.revision;
|
|
1408
|
+
(0, react.useEffect)(() => {
|
|
1409
|
+
if (view?.kind !== "ready" || !view.needsWriteback || revision === void 0 || attemptedRevision.current === revision) return;
|
|
1410
|
+
attemptedRevision.current = revision;
|
|
1411
|
+
const writeback = async () => {
|
|
1412
|
+
try {
|
|
1413
|
+
const operations = replaceDocumentOperations(view.layers.user, view.config);
|
|
1414
|
+
await mutate(settingsOperations(view.layers, operations, resolve), revision);
|
|
1415
|
+
} catch (error) {
|
|
1416
|
+
setFailure({
|
|
1417
|
+
revision,
|
|
1418
|
+
diagnostic: diagnostic(error)
|
|
1419
|
+
});
|
|
1420
|
+
}
|
|
1421
|
+
};
|
|
1422
|
+
writeback();
|
|
1423
|
+
}, [
|
|
1424
|
+
view,
|
|
1425
|
+
revision,
|
|
1426
|
+
resolve,
|
|
1427
|
+
mutate
|
|
1428
|
+
]);
|
|
1429
|
+
const queue = (0, react.useRef)(Promise.resolve());
|
|
1430
|
+
const submit = async (change, displayedRevision) => {
|
|
1431
|
+
if (typeof change !== "function") {
|
|
1432
|
+
if (change.length === 0) return true;
|
|
1433
|
+
if (view === void 0 || !snapshot.writable || displayedRevision === void 0) return false;
|
|
1434
|
+
return mutate(settingsOperations(view.layers, change, resolve), displayedRevision);
|
|
1435
|
+
}
|
|
1436
|
+
const current = read();
|
|
1437
|
+
if (current.status !== "ready" || !current.writable || current.revision === void 0) return false;
|
|
1438
|
+
const layers = {
|
|
1439
|
+
base: current.base,
|
|
1440
|
+
user: current.user
|
|
1441
|
+
};
|
|
1442
|
+
const operations = change(layers);
|
|
1443
|
+
if (operations.length === 0) return true;
|
|
1444
|
+
return mutate(settingsOperations(layers, operations, resolve), current.revision);
|
|
1445
|
+
};
|
|
1446
|
+
const write = (change, expectedRevision = revision) => {
|
|
1447
|
+
const task = queue.current.then(() => submit(change, expectedRevision));
|
|
1448
|
+
queue.current = task.then(() => {}, () => {});
|
|
1449
|
+
return task;
|
|
1450
|
+
};
|
|
1451
|
+
return {
|
|
1452
|
+
view,
|
|
1453
|
+
write,
|
|
1454
|
+
migrationError: failure?.revision === revision ? failure?.diagnostic : void 0
|
|
1455
|
+
};
|
|
1456
|
+
}
|
|
1457
|
+
function replaceDocumentOperations(user, document) {
|
|
1458
|
+
const operations = Object.keys(objectOf$1(user)).filter((key) => !Object.hasOwn(document, key)).map((key) => ({
|
|
1459
|
+
op: "unset",
|
|
1460
|
+
path: [key]
|
|
1461
|
+
}));
|
|
1462
|
+
for (const [key, value] of Object.entries(document)) operations.push({
|
|
1463
|
+
op: "set",
|
|
1464
|
+
path: [key],
|
|
1465
|
+
value
|
|
1466
|
+
});
|
|
1467
|
+
return operations;
|
|
1468
|
+
}
|
|
1469
|
+
function diagnostic(error) {
|
|
1470
|
+
return error instanceof Error ? error.message : String(error);
|
|
1471
|
+
}
|
|
1472
|
+
function isObject$1(value) {
|
|
1473
|
+
return value !== null && typeof value === "object" && !Array.isArray(value);
|
|
1474
|
+
}
|
|
1475
|
+
function objectOf$1(value) {
|
|
1476
|
+
return isObject$1(value) ? value : {};
|
|
1477
|
+
}
|
|
1478
|
+
function merge(base, user) {
|
|
1479
|
+
const result = { ...objectOf$1(base) };
|
|
1480
|
+
for (const [key, value] of Object.entries(objectOf$1(user))) Object.defineProperty(result, key, {
|
|
1481
|
+
value: isObject$1(value) && isObject$1(result[key]) ? merge(result[key], value) : value,
|
|
1482
|
+
enumerable: true,
|
|
1483
|
+
writable: true,
|
|
1484
|
+
configurable: true
|
|
1485
|
+
});
|
|
1486
|
+
return result;
|
|
1487
|
+
}
|
|
1488
|
+
//#endregion
|
|
1489
|
+
//#region ../core/src/client/remote-services.ts
|
|
1490
|
+
/** Whether the catalog has remote services and every one of them is off. */
|
|
1491
|
+
function remoteServicesOff(catalog, resolved) {
|
|
1492
|
+
const remote = Object.keys(catalog).filter((key) => catalog[key].optIn);
|
|
1493
|
+
return remote.length > 0 && remote.every((key) => resolved.connections.get(builtinId(key)).disabled);
|
|
1494
|
+
}
|
|
1495
|
+
/** The fact for the current row settings, recomputed only when the settings snapshot changes. */
|
|
1496
|
+
function remoteServicesOffSource(settings, catalog, resolve) {
|
|
1497
|
+
let cached;
|
|
1498
|
+
const compute = (source) => {
|
|
1499
|
+
if (source.value === void 0) return false;
|
|
1500
|
+
const view = editableSettings(effectiveDocument(source), source, false, resolve);
|
|
1501
|
+
return view.kind === "ready" && remoteServicesOff(catalog, resolve(view.config));
|
|
1502
|
+
};
|
|
1503
|
+
return {
|
|
1504
|
+
getSnapshot() {
|
|
1505
|
+
const source = settings.getSnapshot();
|
|
1506
|
+
if (cached === void 0 || cached.source !== source) cached = {
|
|
1507
|
+
source,
|
|
1508
|
+
off: compute(source)
|
|
1509
|
+
};
|
|
1510
|
+
return cached.off;
|
|
1511
|
+
},
|
|
1512
|
+
subscribe: (listener) => settings.subscribe(listener)
|
|
1513
|
+
};
|
|
1514
|
+
}
|
|
1515
|
+
//#endregion
|
|
1109
1516
|
//#region ../core/src/client/command.ts
|
|
1110
1517
|
/** Shared ids cannot be shadowed by capability-specific option groups. */
|
|
1111
1518
|
function parseSelectionCommandOption(id, parseOptions) {
|
|
@@ -1505,26 +1912,26 @@ window.__ModuleLoader__.load({
|
|
|
1505
1912
|
};
|
|
1506
1913
|
//#endregion
|
|
1507
1914
|
//#region ../core/src/client/settings/sparse.ts
|
|
1508
|
-
const objectOf
|
|
1509
|
-
const isObject
|
|
1915
|
+
const objectOf = (value) => value !== null && typeof value === "object" && !Array.isArray(value) ? value : {};
|
|
1916
|
+
const isObject = (value) => value !== null && typeof value === "object" && !Array.isArray(value);
|
|
1510
1917
|
function equal(a, b) {
|
|
1511
1918
|
if (Object.is(a, b)) return true;
|
|
1512
1919
|
if (Array.isArray(a) || Array.isArray(b)) return Array.isArray(a) && Array.isArray(b) && a.length === b.length && a.every((value, index) => equal(value, b[index]));
|
|
1513
|
-
if (!isObject
|
|
1920
|
+
if (!isObject(a) || !isObject(b)) return false;
|
|
1514
1921
|
const keys = Object.keys(a);
|
|
1515
1922
|
return keys.length === Object.keys(b).length && keys.every((key) => Object.hasOwn(b, key) && equal(a[key], b[key]));
|
|
1516
1923
|
}
|
|
1517
1924
|
/** Remove what an object value shares with its inherited counterpart, key by key. */
|
|
1518
1925
|
function delta(value, inherited) {
|
|
1519
1926
|
if (equal(value, inherited)) return void 0;
|
|
1520
|
-
if (!isObject
|
|
1521
|
-
const base = objectOf
|
|
1927
|
+
if (!isObject(value)) return value;
|
|
1928
|
+
const base = objectOf(inherited);
|
|
1522
1929
|
return Object.fromEntries(Object.entries(value).map(([key, child]) => [key, delta(child, base[key])]).filter(([, child]) => child !== void 0));
|
|
1523
1930
|
}
|
|
1524
1931
|
function documentVersion$1(layers) {
|
|
1525
1932
|
return documentVersion$2({
|
|
1526
|
-
...objectOf
|
|
1527
|
-
...objectOf
|
|
1933
|
+
...objectOf(layers.base),
|
|
1934
|
+
...objectOf(layers.user)
|
|
1528
1935
|
});
|
|
1529
1936
|
}
|
|
1530
1937
|
function assertCurrentVersion(layers) {
|
|
@@ -1541,240 +1948,53 @@ window.__ModuleLoader__.load({
|
|
|
1541
1948
|
const inherited = valueAt(layers.base, path) ?? fallback;
|
|
1542
1949
|
const user = valueAt(layers.user, path);
|
|
1543
1950
|
const ops = [];
|
|
1544
|
-
if (target === void 0 || equal(target, inherited)) {
|
|
1545
|
-
if (user !== void 0) ops.push({
|
|
1546
|
-
op: "unset",
|
|
1547
|
-
path: prunedPath(layers.user, path)
|
|
1548
|
-
});
|
|
1549
|
-
} else {
|
|
1550
|
-
const sparse = delta(target, inherited);
|
|
1551
|
-
if (!equal(sparse, user)) ops.push({
|
|
1552
|
-
op: "set",
|
|
1553
|
-
path: [...path],
|
|
1554
|
-
value: sparse
|
|
1555
|
-
});
|
|
1556
|
-
}
|
|
1557
|
-
if (ops.some((op) => op.op === "set") && objectOf$1(layers.user).version !== spec.version) ops.push({
|
|
1558
|
-
op: "set",
|
|
1559
|
-
path: ["version"],
|
|
1560
|
-
value: spec.version
|
|
1561
|
-
});
|
|
1562
|
-
return ops;
|
|
1563
|
-
}
|
|
1564
|
-
function valueAt(root, path) {
|
|
1565
|
-
return path.reduce((value, key) => objectOf$1(value)[key], root);
|
|
1566
|
-
}
|
|
1567
|
-
/**
|
|
1568
|
-
* The path to unset so no empty object stays behind: removing the only key of
|
|
1569
|
-
* a user-layer object removes that object instead, up to a top-level field.
|
|
1570
|
-
*/
|
|
1571
|
-
function prunedPath(user, path) {
|
|
1572
|
-
let end = path.length;
|
|
1573
|
-
while (end > 1 && Object.keys(objectOf$1(valueAt(user, path.slice(0, end - 1)))).length === 1) end -= 1;
|
|
1574
|
-
return path.slice(0, end);
|
|
1575
|
-
}
|
|
1576
|
-
/** Unset every field this plugin stores in the user layer; inherited values and credentials stay. */
|
|
1577
|
-
function resetSettingsOperations$1(layers) {
|
|
1578
|
-
return Object.keys(objectOf$1(layers.user)).map((key) => ({
|
|
1579
|
-
op: "unset",
|
|
1580
|
-
path: [key]
|
|
1581
|
-
}));
|
|
1582
|
-
}
|
|
1583
|
-
/** Bind the current document version and fields; no predecessor schema is inferred. */
|
|
1584
|
-
function createSparseSettings(spec) {
|
|
1585
|
-
return {
|
|
1586
|
-
documentVersion: (layers) => documentVersion$1(layers),
|
|
1587
|
-
sparseSettingOperations: (layers, path, target, fallback) => sparseSettingOperations$1(spec, layers, path, target, fallback),
|
|
1588
|
-
resetSettingsOperations: (layers) => resetSettingsOperations$1(layers)
|
|
1589
|
-
};
|
|
1590
|
-
}
|
|
1591
|
-
//#endregion
|
|
1592
|
-
//#region ../core/src/client/settings/parts.tsx
|
|
1593
|
-
/** Building blocks shared by the settings sections. */
|
|
1594
|
-
function classNames(...args) {
|
|
1595
|
-
return args.flat(Number.POSITIVE_INFINITY).filter(Boolean).map((arg) => {
|
|
1596
|
-
if (typeof arg === "string") return arg;
|
|
1597
|
-
if (typeof arg === "object" && arg !== null) return Object.entries(arg).filter(([, v]) => Boolean(v)).map(([k]) => k).join(" ");
|
|
1598
|
-
return "";
|
|
1599
|
-
}).filter(Boolean).join(" ");
|
|
1600
|
-
}
|
|
1601
|
-
/** A local schema failure whose diagnostic stays out of the translated message. */
|
|
1602
|
-
var SettingsValidationError = class extends Error {};
|
|
1603
|
-
function createSettingsParts({ classes: css, keys }) {
|
|
1604
|
-
function Section({ title, actions, children }) {
|
|
1605
|
-
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("section", {
|
|
1606
|
-
className: css.section,
|
|
1607
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1608
|
-
className: css.sectionHead,
|
|
1609
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("h4", {
|
|
1610
|
-
className: css.sectionTitle,
|
|
1611
|
-
children: title
|
|
1612
|
-
}), actions]
|
|
1613
|
-
}), children]
|
|
1614
|
-
});
|
|
1615
|
-
}
|
|
1616
|
-
/** Title and hint on the left, one control on the right; wraps under the text on narrow pages. */
|
|
1617
|
-
function SettingRow({ title, hint, children }) {
|
|
1618
|
-
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1619
|
-
className: css.settingRow,
|
|
1620
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1621
|
-
className: css.settingText,
|
|
1622
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
1623
|
-
className: css.settingTitle,
|
|
1624
|
-
children: title
|
|
1625
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
1626
|
-
className: css.hint,
|
|
1627
|
-
children: hint
|
|
1628
|
-
})]
|
|
1629
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
1630
|
-
className: css.settingControl,
|
|
1631
|
-
children
|
|
1632
|
-
})]
|
|
1633
|
-
});
|
|
1634
|
-
}
|
|
1635
|
-
/** A dropdown in the settings pill style, built on the shared Menu. */
|
|
1636
|
-
function SelectMenu({ label, title, value, options, disabled, onChange, compact = false }) {
|
|
1637
|
-
const [open, setOpen] = (0, react.useState)(false);
|
|
1638
|
-
const current = options.find((option) => option.id === value);
|
|
1639
|
-
return /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.Menu, {
|
|
1640
|
-
open,
|
|
1641
|
-
onClose: () => {
|
|
1642
|
-
setOpen(false);
|
|
1643
|
-
},
|
|
1644
|
-
items: options.map((option) => ({
|
|
1645
|
-
id: option.id,
|
|
1646
|
-
label: option.label
|
|
1647
|
-
})),
|
|
1648
|
-
selectedId: value,
|
|
1649
|
-
onSelect: (id) => {
|
|
1650
|
-
setOpen(false);
|
|
1651
|
-
if (id !== value) onChange(id);
|
|
1652
|
-
},
|
|
1653
|
-
align: "end",
|
|
1654
|
-
portal: true,
|
|
1655
|
-
anchor: /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("button", {
|
|
1656
|
-
type: "button",
|
|
1657
|
-
className: compact ? css.selectCompact : css.select,
|
|
1658
|
-
"aria-label": label,
|
|
1659
|
-
title,
|
|
1660
|
-
"aria-haspopup": "menu",
|
|
1661
|
-
"aria-expanded": open,
|
|
1662
|
-
disabled,
|
|
1663
|
-
onClick: () => {
|
|
1664
|
-
setOpen(!open);
|
|
1665
|
-
},
|
|
1666
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
1667
|
-
className: css.selectValue,
|
|
1668
|
-
children: current?.label ?? value
|
|
1669
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.IconChevronDownOutlineRegular, { className: css.selectChevron })]
|
|
1670
|
-
})
|
|
1671
|
-
});
|
|
1672
|
-
}
|
|
1673
|
-
/** Pending state and the last failure of one section's writes. */
|
|
1674
|
-
function useWrite(t) {
|
|
1675
|
-
const [state, setState] = (0, react.useState)({
|
|
1676
|
-
busy: false,
|
|
1677
|
-
error: void 0,
|
|
1678
|
-
errorTitle: void 0
|
|
1679
|
-
});
|
|
1680
|
-
const run = async (work) => {
|
|
1681
|
-
setState({
|
|
1682
|
-
busy: true,
|
|
1683
|
-
error: void 0,
|
|
1684
|
-
errorTitle: void 0
|
|
1685
|
-
});
|
|
1686
|
-
try {
|
|
1687
|
-
const accepted = await work();
|
|
1688
|
-
setState({
|
|
1689
|
-
busy: false,
|
|
1690
|
-
error: accepted ? void 0 : t(keys.refused),
|
|
1691
|
-
errorTitle: void 0
|
|
1692
|
-
});
|
|
1693
|
-
return accepted;
|
|
1694
|
-
} catch (error) {
|
|
1695
|
-
const message = error instanceof Error ? error.message : String(error);
|
|
1696
|
-
const invalid = error instanceof SettingsValidationError;
|
|
1697
|
-
setState({
|
|
1698
|
-
busy: false,
|
|
1699
|
-
error: invalid ? t(keys.invalid) : message || t(keys.failed),
|
|
1700
|
-
errorTitle: invalid ? message : void 0
|
|
1701
|
-
});
|
|
1702
|
-
return false;
|
|
1703
|
-
}
|
|
1704
|
-
};
|
|
1705
|
-
return {
|
|
1706
|
-
...state,
|
|
1707
|
-
run
|
|
1708
|
-
};
|
|
1709
|
-
}
|
|
1710
|
-
function ErrorText({ children, title }) {
|
|
1711
|
-
return children === void 0 ? null : /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
1712
|
-
className: css.error,
|
|
1713
|
-
role: "alert",
|
|
1714
|
-
title,
|
|
1715
|
-
children
|
|
1951
|
+
if (target === void 0 || equal(target, inherited)) {
|
|
1952
|
+
if (user !== void 0) ops.push({
|
|
1953
|
+
op: "unset",
|
|
1954
|
+
path: prunedPath(layers.user, path)
|
|
1716
1955
|
});
|
|
1717
|
-
}
|
|
1718
|
-
|
|
1719
|
-
|
|
1720
|
-
|
|
1721
|
-
|
|
1722
|
-
|
|
1723
|
-
"aria-label": message,
|
|
1724
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("span", {
|
|
1725
|
-
className: css.confirmText,
|
|
1726
|
-
children: message
|
|
1727
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
1728
|
-
className: css.actions,
|
|
1729
|
-
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.Button, {
|
|
1730
|
-
variant: "ghost",
|
|
1731
|
-
size: "sm",
|
|
1732
|
-
onClick: onCancel,
|
|
1733
|
-
children: cancelLabel
|
|
1734
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.Button, {
|
|
1735
|
-
variant: "outline",
|
|
1736
|
-
size: "sm",
|
|
1737
|
-
className: css.danger,
|
|
1738
|
-
disabled,
|
|
1739
|
-
onClick: onConfirm,
|
|
1740
|
-
children: confirmLabel
|
|
1741
|
-
})]
|
|
1742
|
-
})]
|
|
1956
|
+
} else {
|
|
1957
|
+
const sparse = delta(target, inherited);
|
|
1958
|
+
if (!equal(sparse, user)) ops.push({
|
|
1959
|
+
op: "set",
|
|
1960
|
+
path: [...path],
|
|
1961
|
+
value: sparse
|
|
1743
1962
|
});
|
|
1744
1963
|
}
|
|
1964
|
+
if (ops.some((op) => op.op === "set") && objectOf(layers.user).version !== spec.version) ops.push({
|
|
1965
|
+
op: "set",
|
|
1966
|
+
path: ["version"],
|
|
1967
|
+
value: spec.version
|
|
1968
|
+
});
|
|
1969
|
+
return ops;
|
|
1970
|
+
}
|
|
1971
|
+
function valueAt(root, path) {
|
|
1972
|
+
return path.reduce((value, key) => objectOf(value)[key], root);
|
|
1973
|
+
}
|
|
1974
|
+
/**
|
|
1975
|
+
* The path to unset so no empty object stays behind: removing the only key of
|
|
1976
|
+
* a user-layer object removes that object instead, up to a top-level field.
|
|
1977
|
+
*/
|
|
1978
|
+
function prunedPath(user, path) {
|
|
1979
|
+
let end = path.length;
|
|
1980
|
+
while (end > 1 && Object.keys(objectOf(valueAt(user, path.slice(0, end - 1)))).length === 1) end -= 1;
|
|
1981
|
+
return path.slice(0, end);
|
|
1982
|
+
}
|
|
1983
|
+
/** Unset every field this plugin stores in the user layer; inherited values and credentials stay. */
|
|
1984
|
+
function resetSettingsOperations$1(layers) {
|
|
1985
|
+
return Object.keys(objectOf(layers.user)).map((key) => ({
|
|
1986
|
+
op: "unset",
|
|
1987
|
+
path: [key]
|
|
1988
|
+
}));
|
|
1989
|
+
}
|
|
1990
|
+
/** Bind the current document version and fields; no predecessor schema is inferred. */
|
|
1991
|
+
function createSparseSettings(spec) {
|
|
1745
1992
|
return {
|
|
1746
|
-
|
|
1747
|
-
|
|
1748
|
-
|
|
1749
|
-
ErrorText,
|
|
1750
|
-
ConfirmRow,
|
|
1751
|
-
useWrite
|
|
1993
|
+
documentVersion: (layers) => documentVersion$1(layers),
|
|
1994
|
+
sparseSettingOperations: (layers, path, target, fallback) => sparseSettingOperations$1(spec, layers, path, target, fallback),
|
|
1995
|
+
resetSettingsOperations: (layers) => resetSettingsOperations$1(layers)
|
|
1752
1996
|
};
|
|
1753
1997
|
}
|
|
1754
|
-
function applyOps(user, ops) {
|
|
1755
|
-
const root = structuredClone(user !== null && typeof user === "object" && !Array.isArray(user) ? user : {});
|
|
1756
|
-
for (const op of ops) {
|
|
1757
|
-
if (op.path.length === 0) continue;
|
|
1758
|
-
if (op.op === "set") {
|
|
1759
|
-
let current = root;
|
|
1760
|
-
for (let i = 0; i < op.path.length - 1; i++) {
|
|
1761
|
-
const seg = op.path[i];
|
|
1762
|
-
if (current[seg] === null || typeof current[seg] !== "object" || Array.isArray(current[seg])) current[seg] = {};
|
|
1763
|
-
current = current[seg];
|
|
1764
|
-
}
|
|
1765
|
-
current[op.path.at(-1)] = structuredClone(op.value);
|
|
1766
|
-
} else if (op.op === "unset") {
|
|
1767
|
-
let current = root;
|
|
1768
|
-
for (let i = 0; i < op.path.length - 1; i++) {
|
|
1769
|
-
const seg = op.path[i];
|
|
1770
|
-
if (current[seg] === null || typeof current[seg] !== "object" || Array.isArray(current[seg])) break;
|
|
1771
|
-
current = current[seg];
|
|
1772
|
-
}
|
|
1773
|
-
delete current[op.path.at(-1)];
|
|
1774
|
-
}
|
|
1775
|
-
}
|
|
1776
|
-
return root;
|
|
1777
|
-
}
|
|
1778
1998
|
//#endregion
|
|
1779
1999
|
//#region ../core/src/client/settings/CredentialEditor.tsx
|
|
1780
2000
|
/** Write-only key entry: the value goes to DSH Credentials and never into settings. */
|
|
@@ -2217,14 +2437,25 @@ window.__ModuleLoader__.load({
|
|
|
2217
2437
|
function adapterKeys(catalog) {
|
|
2218
2438
|
return Object.entries(catalog).filter(([, info]) => info.kind === "adapter").map(([key]) => key);
|
|
2219
2439
|
}
|
|
2440
|
+
/** A built-in entry's override as stored, its label on one line as the grammar reads it. */
|
|
2220
2441
|
function builtinOverride(config, key) {
|
|
2221
2442
|
const stored = config.connections === void 0 ? void 0 : config.connections[builtinId(key)];
|
|
2222
|
-
|
|
2443
|
+
if (stored === void 0) return {};
|
|
2444
|
+
return stored.label === void 0 ? stored : {
|
|
2445
|
+
...stored,
|
|
2446
|
+
label: singleLine(stored.label)
|
|
2447
|
+
};
|
|
2223
2448
|
}
|
|
2224
|
-
/** Custom connections in document order; the document has passed the capability's validation. */
|
|
2449
|
+
/** Custom connections in document order, labels on one line; the document has passed the capability's validation. */
|
|
2225
2450
|
function customConnections(config) {
|
|
2226
2451
|
if (config.connections === void 0) return [];
|
|
2227
|
-
return Object.entries(config.connections).filter(([id]) => CUSTOM_CONNECTION_ID.test(id)).map(([id,
|
|
2452
|
+
return Object.entries(config.connections).filter(([id]) => CUSTOM_CONNECTION_ID.test(id)).map(([id, stored]) => {
|
|
2453
|
+
const connection = stored;
|
|
2454
|
+
return [id, {
|
|
2455
|
+
...connection,
|
|
2456
|
+
label: singleLine(connection.label)
|
|
2457
|
+
}];
|
|
2458
|
+
});
|
|
2228
2459
|
}
|
|
2229
2460
|
/** Built-in connections default to the anonymous route where one exists. */
|
|
2230
2461
|
function builtinAccess(info, override) {
|
|
@@ -2560,15 +2791,19 @@ window.__ModuleLoader__.load({
|
|
|
2560
2791
|
});
|
|
2561
2792
|
function ServicesSection(props) {
|
|
2562
2793
|
const catalogKeys = Object.keys(catalog);
|
|
2563
|
-
|
|
2794
|
+
const optIn = catalogKeys.some((key) => catalog[key].optIn);
|
|
2795
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(Section, {
|
|
2564
2796
|
title: props.t(keys["services.title"]),
|
|
2565
|
-
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)("
|
|
2797
|
+
children: [optIn ? /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
2798
|
+
className: css.note,
|
|
2799
|
+
children: props.t(keys["services.optInNotice"])
|
|
2800
|
+
}) : null, /* @__PURE__ */ (0, react_jsx_runtime.jsx)("ul", {
|
|
2566
2801
|
className: css.list,
|
|
2567
2802
|
children: catalogKeys.map((key) => /* @__PURE__ */ (0, react_jsx_runtime.jsx)(ServiceRow, {
|
|
2568
2803
|
catalogKey: key,
|
|
2569
2804
|
...props
|
|
2570
2805
|
}, key))
|
|
2571
|
-
})
|
|
2806
|
+
})]
|
|
2572
2807
|
});
|
|
2573
2808
|
}
|
|
2574
2809
|
function ServiceRow({ catalogKey, doc, write, credentials, saveCredential, t }) {
|
|
@@ -2584,18 +2819,18 @@ window.__ModuleLoader__.load({
|
|
|
2584
2819
|
const credential = builtinCredential(info, override);
|
|
2585
2820
|
const credentialRef = credential === void 0 ? void 0 : credential.ref;
|
|
2586
2821
|
const credentialStatus = credentialRef === void 0 ? void 0 : credentials[credentialRef];
|
|
2587
|
-
const enabled = override.disabled
|
|
2822
|
+
const enabled = !(override.disabled ?? info.optIn);
|
|
2588
2823
|
const disabled = !doc.editable || action.busy;
|
|
2589
|
-
const operations = (path, target, fallback) => sparse.sparseSettingOperations(
|
|
2824
|
+
const operations = (layers, path, target, fallback) => sparse.sparseSettingOperations(layers, [
|
|
2590
2825
|
"connections",
|
|
2591
2826
|
connectionId,
|
|
2592
2827
|
...path
|
|
2593
2828
|
], target, fallback);
|
|
2594
|
-
const save = (path, target, fallback) => action.run(() => write(operations(path, target, fallback)));
|
|
2829
|
+
const save = (path, target, fallback) => action.run(() => write((layers) => operations(layers, path, target, fallback)));
|
|
2595
2830
|
const stored = override.options === void 0 ? {} : override.options;
|
|
2596
|
-
const saveOptions = (changes) => action.run(() => {
|
|
2597
|
-
let layers =
|
|
2598
|
-
return
|
|
2831
|
+
const saveOptions = (changes) => action.run(() => write((initial) => {
|
|
2832
|
+
let layers = initial;
|
|
2833
|
+
return Object.entries(changes).flatMap(([option, value]) => {
|
|
2599
2834
|
const next = sparse.sparseSettingOperations(layers, [
|
|
2600
2835
|
"connections",
|
|
2601
2836
|
connectionId,
|
|
@@ -2607,15 +2842,22 @@ window.__ModuleLoader__.load({
|
|
|
2607
2842
|
user: applyOps(layers.user, next)
|
|
2608
2843
|
};
|
|
2609
2844
|
return next;
|
|
2610
|
-
})
|
|
2611
|
-
});
|
|
2612
|
-
/**
|
|
2845
|
+
});
|
|
2846
|
+
}));
|
|
2847
|
+
/**
|
|
2848
|
+
* The keyless route takes only the options it accepts; the rest go in the
|
|
2849
|
+
* same write. Which ones those are is read from the layers the write runs
|
|
2850
|
+
* on: options changed while it waited stay as they are now.
|
|
2851
|
+
*/
|
|
2613
2852
|
const switchAccess = (next) => {
|
|
2614
2853
|
if (next === "api-key") return save(["access"], next, "keyless");
|
|
2615
|
-
|
|
2616
|
-
|
|
2617
|
-
|
|
2618
|
-
|
|
2854
|
+
return action.run(() => write((layers) => {
|
|
2855
|
+
const current = builtinOverride(effectiveDocument(layers), catalogKey).options;
|
|
2856
|
+
const options = current === void 0 ? {} : current;
|
|
2857
|
+
const rejected = keylessRejected(info.options, options);
|
|
2858
|
+
const kept = Object.fromEntries(Object.entries(options).filter(([option]) => !rejected.includes(option)));
|
|
2859
|
+
return [...operations(layers, ["access"], next, "keyless"), ...rejected.length === 0 ? [] : operations(layers, ["options"], Object.keys(kept).length === 0 ? void 0 : kept)];
|
|
2860
|
+
}));
|
|
2619
2861
|
};
|
|
2620
2862
|
const note = notes[catalogKey];
|
|
2621
2863
|
const extra = extras[catalogKey];
|
|
@@ -2665,7 +2907,7 @@ window.__ModuleLoader__.load({
|
|
|
2665
2907
|
checked: enabled,
|
|
2666
2908
|
label: t(keys["services.enable"], { name }),
|
|
2667
2909
|
disabled,
|
|
2668
|
-
onChange: (next) => void save(["disabled"], !next,
|
|
2910
|
+
onChange: (next) => void save(["disabled"], !next, info.optIn)
|
|
2669
2911
|
})]
|
|
2670
2912
|
})
|
|
2671
2913
|
]
|
|
@@ -2890,7 +3132,7 @@ window.__ModuleLoader__.load({
|
|
|
2890
3132
|
const action = useWrite(t);
|
|
2891
3133
|
const disabled = !doc.editable || action.busy;
|
|
2892
3134
|
const save = (path, target, fallback) => {
|
|
2893
|
-
action.run(() => write(sparse.sparseSettingOperations(
|
|
3135
|
+
action.run(() => write((layers) => sparse.sparseSettingOperations(layers, path, target, fallback)));
|
|
2894
3136
|
};
|
|
2895
3137
|
const missing = defaultConnection !== void 0 && !choices.some((choice) => choice.id === defaultConnection);
|
|
2896
3138
|
const warning = missing ? t(keys.connectionMissing, { id: defaultConnection }) : defaultAvailability && (defaultAvailability.disabled || configurationState(true, defaultAvailability.access, defaultAvailability.credentialStatus) === "warning") ? defaultAvailability.warning : void 0;
|
|
@@ -2937,6 +3179,53 @@ window.__ModuleLoader__.load({
|
|
|
2937
3179
|
};
|
|
2938
3180
|
}
|
|
2939
3181
|
//#endregion
|
|
3182
|
+
//#region ../core/src/client/settings/EnhancedToolsSection.tsx
|
|
3183
|
+
/**
|
|
3184
|
+
* The row's Enhanced tools switch (docs/design.md, "开关与同意"): what turning
|
|
3185
|
+
* it on lets the Agent do, and what the operator agrees to by doing so.
|
|
3186
|
+
*/
|
|
3187
|
+
function createEnhancedToolsSection({ classes: css, parts: { Section, ErrorText, useWrite }, sparse, keys }) {
|
|
3188
|
+
return function EnhancedToolsSection({ doc, write, t }) {
|
|
3189
|
+
const id = (0, react.useId)();
|
|
3190
|
+
const action = useWrite(t);
|
|
3191
|
+
const enabled = doc.config.enhancedTools ?? false;
|
|
3192
|
+
const save = (next) => action.run(() => write((layers) => sparse.sparseSettingOperations(layers, ["enhancedTools"], next, false)));
|
|
3193
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)(Section, {
|
|
3194
|
+
title: t(keys.title),
|
|
3195
|
+
titleId: id + "-title",
|
|
3196
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
3197
|
+
className: css.settingRow,
|
|
3198
|
+
role: "group",
|
|
3199
|
+
"aria-labelledby": id + "-title",
|
|
3200
|
+
"aria-describedby": id + "-description " + id + "-consent",
|
|
3201
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsxs)("div", {
|
|
3202
|
+
className: css.settingText,
|
|
3203
|
+
children: [/* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3204
|
+
id: id + "-description",
|
|
3205
|
+
className: css.settingLead,
|
|
3206
|
+
children: t(keys.description)
|
|
3207
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3208
|
+
id: id + "-consent",
|
|
3209
|
+
className: css.hint,
|
|
3210
|
+
children: t(keys.consent)
|
|
3211
|
+
})]
|
|
3212
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)("div", {
|
|
3213
|
+
className: css.settingControl,
|
|
3214
|
+
children: /* @__PURE__ */ (0, react_jsx_runtime.jsx)(_deepseek_ai_dsh_client_ui_primitives.Switch, {
|
|
3215
|
+
checked: enabled,
|
|
3216
|
+
label: t(keys.title),
|
|
3217
|
+
disabled: !doc.editable || action.busy,
|
|
3218
|
+
onChange: (next) => void save(next)
|
|
3219
|
+
})
|
|
3220
|
+
})]
|
|
3221
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(ErrorText, {
|
|
3222
|
+
title: action.errorTitle,
|
|
3223
|
+
children: action.error
|
|
3224
|
+
})]
|
|
3225
|
+
});
|
|
3226
|
+
};
|
|
3227
|
+
}
|
|
3228
|
+
//#endregion
|
|
2940
3229
|
//#region ../core/src/client/settings/ResetSection.tsx
|
|
2941
3230
|
function createResetSection({ classes: css, keys, parts: { ConfirmRow, ErrorText, useWrite }, sparse }) {
|
|
2942
3231
|
return function ResetSection({ doc, write, t }) {
|
|
@@ -2970,175 +3259,40 @@ window.__ModuleLoader__.load({
|
|
|
2970
3259
|
disabled,
|
|
2971
3260
|
onClick: () => {
|
|
2972
3261
|
setConfirming(true);
|
|
2973
|
-
},
|
|
2974
|
-
children: t(keys["reset.button"])
|
|
2975
|
-
})]
|
|
2976
|
-
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(ErrorText, {
|
|
2977
|
-
title: action.errorTitle,
|
|
2978
|
-
children: action.error
|
|
2979
|
-
})]
|
|
2980
|
-
});
|
|
2981
|
-
};
|
|
2982
|
-
}
|
|
2983
|
-
//#endregion
|
|
2984
|
-
//#region ../core/src/client/settings/RouteNotice.tsx
|
|
2985
|
-
function createRouteNotice({ classes: css, keys, other }) {
|
|
2986
|
-
return function RouteNotice({ route, t }) {
|
|
2987
|
-
let text;
|
|
2988
|
-
switch (route.kind) {
|
|
2989
|
-
case "this": return null;
|
|
2990
|
-
case "unknown":
|
|
2991
|
-
text = t(keys.unknown);
|
|
2992
|
-
break;
|
|
2993
|
-
case "auto":
|
|
2994
|
-
text = t(keys.auto, { id: route.providerId });
|
|
2995
|
-
break;
|
|
2996
|
-
case "other": text = other?.(route, t) ?? t(keys.other, {
|
|
2997
|
-
provider: route.provider,
|
|
2998
|
-
id: route.providerId
|
|
2999
|
-
});
|
|
3000
|
-
}
|
|
3001
|
-
return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3002
|
-
className: css.warning,
|
|
3003
|
-
role: "status",
|
|
3004
|
-
children: text
|
|
3005
|
-
});
|
|
3006
|
-
};
|
|
3007
|
-
}
|
|
3008
|
-
//#endregion
|
|
3009
|
-
//#region ../core/src/client/settings/document.ts
|
|
3010
|
-
/** ConfigForm.value is schema-projected; the raw layers retain unknown fields for validation. */
|
|
3011
|
-
function effectiveDocument(snapshot) {
|
|
3012
|
-
return merge(snapshot.base, snapshot.user);
|
|
3013
|
-
}
|
|
3014
|
-
/** Validate before exposing normal editors; only successful older migrations need writeback. */
|
|
3015
|
-
function editableSettings(raw, layers, writable, resolve, migrations = SETTINGS_MIGRATIONS) {
|
|
3016
|
-
try {
|
|
3017
|
-
const version = documentVersion$2(raw, migrations.currentVersion);
|
|
3018
|
-
const config = migrateDocument(raw, migrations);
|
|
3019
|
-
resolve(config);
|
|
3020
|
-
return {
|
|
3021
|
-
kind: "ready",
|
|
3022
|
-
config,
|
|
3023
|
-
layers,
|
|
3024
|
-
needsWriteback: writable && version.kind === "older"
|
|
3025
|
-
};
|
|
3026
|
-
} catch (error) {
|
|
3027
|
-
return {
|
|
3028
|
-
kind: "invalid",
|
|
3029
|
-
diagnostic: diagnostic(error),
|
|
3030
|
-
layers,
|
|
3031
|
-
needsWriteback: false
|
|
3032
|
-
};
|
|
3033
|
-
}
|
|
3034
|
-
}
|
|
3035
|
-
/** Check the exact recursively overlaid candidate that the settings store will persist. */
|
|
3036
|
-
function settingsOperations(layers, operations, resolve) {
|
|
3037
|
-
try {
|
|
3038
|
-
const candidate = effectiveDocument({
|
|
3039
|
-
base: layers.base,
|
|
3040
|
-
user: applyOps(layers.user, operations)
|
|
3041
|
-
});
|
|
3042
|
-
const result = [...operations];
|
|
3043
|
-
if (result.some((op) => op.op === "set") && candidate.version === void 0) {
|
|
3044
|
-
result.push({
|
|
3045
|
-
op: "set",
|
|
3046
|
-
path: ["version"],
|
|
3047
|
-
value: 2
|
|
3048
|
-
});
|
|
3049
|
-
candidate.version = 2;
|
|
3050
|
-
}
|
|
3051
|
-
resolve(candidate);
|
|
3052
|
-
return result;
|
|
3053
|
-
} catch (error) {
|
|
3054
|
-
throw new SettingsValidationError(diagnostic(error));
|
|
3055
|
-
}
|
|
3056
|
-
}
|
|
3057
|
-
/** Share validation, revision fencing and automatic future migrations between both pages. */
|
|
3058
|
-
function useSettingsDocument(snapshot, resolve, mutate, migrations = SETTINGS_MIGRATIONS) {
|
|
3059
|
-
const view = (0, react.useMemo)(() => {
|
|
3060
|
-
if (snapshot.status === "unavailable" || snapshot.value === void 0 || snapshot.revision === void 0) return void 0;
|
|
3061
|
-
const result = editableSettings(effectiveDocument(snapshot), {
|
|
3062
|
-
base: snapshot.base,
|
|
3063
|
-
user: snapshot.user
|
|
3064
|
-
}, snapshot.writable, resolve, migrations);
|
|
3065
|
-
if (snapshot.diagnostic === void 0) return result;
|
|
3066
|
-
return {
|
|
3067
|
-
kind: "invalid",
|
|
3068
|
-
layers: result.layers,
|
|
3069
|
-
needsWriteback: false,
|
|
3070
|
-
diagnostic: result.kind === "invalid" ? result.diagnostic + "; " + snapshot.diagnostic : snapshot.diagnostic
|
|
3071
|
-
};
|
|
3072
|
-
}, [
|
|
3073
|
-
snapshot,
|
|
3074
|
-
resolve,
|
|
3075
|
-
migrations
|
|
3076
|
-
]);
|
|
3077
|
-
const attemptedRevision = (0, react.useRef)(void 0);
|
|
3078
|
-
const [failure, setFailure] = (0, react.useState)();
|
|
3079
|
-
const revision = snapshot.revision;
|
|
3080
|
-
(0, react.useEffect)(() => {
|
|
3081
|
-
if (view?.kind !== "ready" || !view.needsWriteback || revision === void 0 || attemptedRevision.current === revision) return;
|
|
3082
|
-
attemptedRevision.current = revision;
|
|
3083
|
-
const writeback = async () => {
|
|
3084
|
-
try {
|
|
3085
|
-
const operations = replaceDocumentOperations(view.layers.user, view.config);
|
|
3086
|
-
await mutate(settingsOperations(view.layers, operations, resolve), revision);
|
|
3087
|
-
} catch (error) {
|
|
3088
|
-
setFailure({
|
|
3089
|
-
revision,
|
|
3090
|
-
diagnostic: diagnostic(error)
|
|
3091
|
-
});
|
|
3092
|
-
}
|
|
3093
|
-
};
|
|
3094
|
-
writeback();
|
|
3095
|
-
}, [
|
|
3096
|
-
view,
|
|
3097
|
-
revision,
|
|
3098
|
-
resolve,
|
|
3099
|
-
mutate
|
|
3100
|
-
]);
|
|
3101
|
-
const write = async (operations, expectedRevision = revision) => {
|
|
3102
|
-
if (operations.length === 0) return true;
|
|
3103
|
-
if (view === void 0 || !snapshot.writable || expectedRevision === void 0) return false;
|
|
3104
|
-
return mutate(settingsOperations(view.layers, operations, resolve), expectedRevision);
|
|
3105
|
-
};
|
|
3106
|
-
return {
|
|
3107
|
-
view,
|
|
3108
|
-
write,
|
|
3109
|
-
migrationError: failure?.revision === revision ? failure?.diagnostic : void 0
|
|
3262
|
+
},
|
|
3263
|
+
children: t(keys["reset.button"])
|
|
3264
|
+
})]
|
|
3265
|
+
}), /* @__PURE__ */ (0, react_jsx_runtime.jsx)(ErrorText, {
|
|
3266
|
+
title: action.errorTitle,
|
|
3267
|
+
children: action.error
|
|
3268
|
+
})]
|
|
3269
|
+
});
|
|
3110
3270
|
};
|
|
3111
3271
|
}
|
|
3112
|
-
|
|
3113
|
-
|
|
3114
|
-
|
|
3115
|
-
|
|
3116
|
-
|
|
3117
|
-
|
|
3118
|
-
|
|
3119
|
-
|
|
3120
|
-
|
|
3121
|
-
|
|
3122
|
-
|
|
3123
|
-
|
|
3124
|
-
|
|
3125
|
-
|
|
3126
|
-
|
|
3127
|
-
|
|
3128
|
-
|
|
3129
|
-
|
|
3130
|
-
|
|
3131
|
-
|
|
3132
|
-
|
|
3133
|
-
|
|
3134
|
-
|
|
3135
|
-
|
|
3136
|
-
value: isObject(value) && isObject(result[key]) ? merge(result[key], value) : value,
|
|
3137
|
-
enumerable: true,
|
|
3138
|
-
writable: true,
|
|
3139
|
-
configurable: true
|
|
3140
|
-
});
|
|
3141
|
-
return result;
|
|
3272
|
+
//#endregion
|
|
3273
|
+
//#region ../core/src/client/settings/RouteNotice.tsx
|
|
3274
|
+
function createRouteNotice({ classes: css, keys, other }) {
|
|
3275
|
+
return function RouteNotice({ route, t }) {
|
|
3276
|
+
let text;
|
|
3277
|
+
switch (route.kind) {
|
|
3278
|
+
case "this": return null;
|
|
3279
|
+
case "unknown":
|
|
3280
|
+
text = t(keys.unknown);
|
|
3281
|
+
break;
|
|
3282
|
+
case "auto":
|
|
3283
|
+
text = t(keys.auto, { id: route.providerId });
|
|
3284
|
+
break;
|
|
3285
|
+
case "other": text = other?.(route, t) ?? t(keys.other, {
|
|
3286
|
+
provider: route.provider,
|
|
3287
|
+
id: route.providerId
|
|
3288
|
+
});
|
|
3289
|
+
}
|
|
3290
|
+
return /* @__PURE__ */ (0, react_jsx_runtime.jsx)("p", {
|
|
3291
|
+
className: css.warning,
|
|
3292
|
+
role: "status",
|
|
3293
|
+
children: text
|
|
3294
|
+
});
|
|
3295
|
+
};
|
|
3142
3296
|
}
|
|
3143
3297
|
//#endregion
|
|
3144
3298
|
//#region ../core/src/client/settings/secret-diagnostics.ts
|
|
@@ -3248,7 +3402,7 @@ window.__ModuleLoader__.load({
|
|
|
3248
3402
|
const options = connection.options === void 0 ? {} : connection.options;
|
|
3249
3403
|
const fields = {
|
|
3250
3404
|
id,
|
|
3251
|
-
label: connection.label,
|
|
3405
|
+
label: singleLine(connection.label),
|
|
3252
3406
|
credentialRef: connection.credentialRef,
|
|
3253
3407
|
endpoint: connection.endpoint === void 0 ? "" : connection.endpoint,
|
|
3254
3408
|
options: Object.fromEntries(Object.entries(options).map(([name, value]) => [name, fieldText(value)]))
|
|
@@ -3322,7 +3476,7 @@ window.__ModuleLoader__.load({
|
|
|
3322
3476
|
const form = {
|
|
3323
3477
|
...input,
|
|
3324
3478
|
id: input.id.trim(),
|
|
3325
|
-
label: input.label
|
|
3479
|
+
label: singleLine(input.label),
|
|
3326
3480
|
credentialRef: input.credentialRef.trim(),
|
|
3327
3481
|
endpoint: input.endpoint.trim()
|
|
3328
3482
|
};
|
|
@@ -3841,7 +3995,7 @@ window.__ModuleLoader__.load({
|
|
|
3841
3995
|
const disabled = !doc.editable || action.busy;
|
|
3842
3996
|
const userConnections = doc.layers.user?.connections;
|
|
3843
3997
|
const removable = userConnections !== void 0 && Object.hasOwn(userConnections, id);
|
|
3844
|
-
const save = (path, target, fallback) => action.run(() => write(sparse.sparseSettingOperations(
|
|
3998
|
+
const save = (path, target, fallback) => action.run(() => write((layers) => sparse.sparseSettingOperations(layers, [
|
|
3845
3999
|
"connections",
|
|
3846
4000
|
id,
|
|
3847
4001
|
...path
|
|
@@ -3973,6 +4127,49 @@ window.__ModuleLoader__.load({
|
|
|
3973
4127
|
"searchContextSize"
|
|
3974
4128
|
];
|
|
3975
4129
|
//#endregion
|
|
4130
|
+
//#region src/settings/resolve.ts
|
|
4131
|
+
const defaultsSchema = zod.z.strictObject({ freshness: zod.z.enum(FRESHNESS).default("auto") });
|
|
4132
|
+
/** Pure sparse resolution shared by Host and browser. */
|
|
4133
|
+
function resolveSettings(document = {}) {
|
|
4134
|
+
const resolved = resolveDocument({
|
|
4135
|
+
catalog: CATALOG,
|
|
4136
|
+
protocols: MODEL_PROTOCOLS,
|
|
4137
|
+
document,
|
|
4138
|
+
retiredFields: RETIRED_FIELDS,
|
|
4139
|
+
defaults: {
|
|
4140
|
+
schema: defaultsSchema,
|
|
4141
|
+
defaultConnection: DEFAULT_CONNECTION
|
|
4142
|
+
},
|
|
4143
|
+
capabilityLabel: "search"
|
|
4144
|
+
});
|
|
4145
|
+
const connections = /* @__PURE__ */ new Map();
|
|
4146
|
+
for (const [id, connection] of resolved.connections) {
|
|
4147
|
+
const { catalogKey, ...base } = connection;
|
|
4148
|
+
switch (base.kind) {
|
|
4149
|
+
case "local": throw new Error("search catalog cannot contain a local connection");
|
|
4150
|
+
case "model":
|
|
4151
|
+
connections.set(id, base);
|
|
4152
|
+
break;
|
|
4153
|
+
case "native":
|
|
4154
|
+
connections.set(id, {
|
|
4155
|
+
...base,
|
|
4156
|
+
kind: "native",
|
|
4157
|
+
native: catalogKey
|
|
4158
|
+
});
|
|
4159
|
+
break;
|
|
4160
|
+
case "adapter": connections.set(id, {
|
|
4161
|
+
...base,
|
|
4162
|
+
kind: "adapter",
|
|
4163
|
+
adapter: catalogKey
|
|
4164
|
+
});
|
|
4165
|
+
}
|
|
4166
|
+
}
|
|
4167
|
+
return {
|
|
4168
|
+
...resolved,
|
|
4169
|
+
connections
|
|
4170
|
+
};
|
|
4171
|
+
}
|
|
4172
|
+
//#endregion
|
|
3976
4173
|
//#region src/client/connections.ts
|
|
3977
4174
|
/** The Session-model connection keeps its catalog name only until the operator renames it; that name is localized. */
|
|
3978
4175
|
function connectionLabel(connection, t) {
|
|
@@ -4134,49 +4331,6 @@ window.__ModuleLoader__.load({
|
|
|
4134
4331
|
});
|
|
4135
4332
|
}
|
|
4136
4333
|
//#endregion
|
|
4137
|
-
//#region src/settings/resolve.ts
|
|
4138
|
-
const defaultsSchema = zod.z.strictObject({ freshness: zod.z.enum(FRESHNESS).default("auto") });
|
|
4139
|
-
/** Pure sparse resolution shared by Host and browser. */
|
|
4140
|
-
function resolveSettings(document = {}) {
|
|
4141
|
-
const resolved = resolveDocument({
|
|
4142
|
-
catalog: CATALOG,
|
|
4143
|
-
protocols: MODEL_PROTOCOLS,
|
|
4144
|
-
document,
|
|
4145
|
-
retiredFields: RETIRED_FIELDS,
|
|
4146
|
-
defaults: {
|
|
4147
|
-
schema: defaultsSchema,
|
|
4148
|
-
defaultConnection: DEFAULT_CONNECTION
|
|
4149
|
-
},
|
|
4150
|
-
capabilityLabel: "search"
|
|
4151
|
-
});
|
|
4152
|
-
const connections = /* @__PURE__ */ new Map();
|
|
4153
|
-
for (const [id, connection] of resolved.connections) {
|
|
4154
|
-
const { catalogKey, ...base } = connection;
|
|
4155
|
-
switch (base.kind) {
|
|
4156
|
-
case "local": throw new Error("search catalog cannot contain a local connection");
|
|
4157
|
-
case "model":
|
|
4158
|
-
connections.set(id, base);
|
|
4159
|
-
break;
|
|
4160
|
-
case "native":
|
|
4161
|
-
connections.set(id, {
|
|
4162
|
-
...base,
|
|
4163
|
-
kind: "native",
|
|
4164
|
-
native: catalogKey
|
|
4165
|
-
});
|
|
4166
|
-
break;
|
|
4167
|
-
case "adapter": connections.set(id, {
|
|
4168
|
-
...base,
|
|
4169
|
-
kind: "adapter",
|
|
4170
|
-
adapter: catalogKey
|
|
4171
|
-
});
|
|
4172
|
-
}
|
|
4173
|
-
}
|
|
4174
|
-
return {
|
|
4175
|
-
...resolved,
|
|
4176
|
-
connections
|
|
4177
|
-
};
|
|
4178
|
-
}
|
|
4179
|
-
//#endregion
|
|
4180
4334
|
//#region src/client/credentials.ts
|
|
4181
4335
|
/** The DSH credential a connection names; the Session-model connection uses the Session route's own. */
|
|
4182
4336
|
function credentialRefsOf(connection) {
|
|
@@ -4275,6 +4429,10 @@ window.__ModuleLoader__.load({
|
|
|
4275
4429
|
"defaults.showSelectorHint": "When hidden, switch the current conversation with /setup-search.",
|
|
4276
4430
|
"defaults.freshnessKeyOnly": "{name} (personal key)",
|
|
4277
4431
|
"services.title": "Search connections",
|
|
4432
|
+
"services.optInNotice": "Remote services are off by default.",
|
|
4433
|
+
"enhanced.title": "Enhanced tools",
|
|
4434
|
+
"enhanced.description": "Lets the Agent pick which enabled service runs a search with web_search_enhanced, and see the choices with list_web_search_providers. Applies to conversations started afterwards.",
|
|
4435
|
+
"enhanced.consent": "Turning this on means you agree that when the Agent picks a service, the query is sent to that service.",
|
|
4278
4436
|
"services.enable": "Enable {name}",
|
|
4279
4437
|
"services.configure": "Configure",
|
|
4280
4438
|
"services.configureLabel": "Configure {name}",
|
|
@@ -4488,7 +4646,7 @@ window.__ModuleLoader__.load({
|
|
|
4488
4646
|
"freshness.auto": "自动",
|
|
4489
4647
|
"freshness.fresh": "24 小时内",
|
|
4490
4648
|
"freshness.realtime": "实时",
|
|
4491
|
-
"status.disabled": "{name}
|
|
4649
|
+
"status.disabled": "{name} 未在设置中启用。",
|
|
4492
4650
|
"status.needsCredential": "需要 API Key",
|
|
4493
4651
|
"status.needsAccount": "需要 DeepSeek 账号或 API Key",
|
|
4494
4652
|
"status.unsupported": "本版本不支持 {name}。",
|
|
@@ -4501,7 +4659,7 @@ window.__ModuleLoader__.load({
|
|
|
4501
4659
|
"selector.freshnessIgnored": "{name} 不支持此偏好,选择不会生效。",
|
|
4502
4660
|
"selector.offRow": "关闭",
|
|
4503
4661
|
"write.conflict": "搜索设置已在别处更改,菜单已显示最新选择。",
|
|
4504
|
-
"write.unavailable": "
|
|
4662
|
+
"write.unavailable": "该连接未启用或已移除。",
|
|
4505
4663
|
"write.failed": "保存失败,请重试。",
|
|
4506
4664
|
"command.label": "搜索连接",
|
|
4507
4665
|
"command.description": "切换当前会话的搜索连接与内容实时性",
|
|
@@ -4532,10 +4690,14 @@ window.__ModuleLoader__.load({
|
|
|
4532
4690
|
"defaults.showSelectorHint": "隐藏后可用 /setup-search 切换当前会话。",
|
|
4533
4691
|
"defaults.freshnessKeyOnly": "{name}(个人密钥)",
|
|
4534
4692
|
"services.title": "搜索连接",
|
|
4693
|
+
"services.optInNotice": "远程服务默认关闭。",
|
|
4694
|
+
"enhanced.title": "增强工具",
|
|
4695
|
+
"enhanced.description": "让 Agent 用 web_search_enhanced 在已启用的服务中自行选择本次搜索用哪个,并用 list_web_search_providers 查看可选项。只影响之后新建的会话。",
|
|
4696
|
+
"enhanced.consent": "打开即表示同意:Agent 选用某个服务时,查询会发送给该服务。",
|
|
4535
4697
|
"services.enable": "启用 {name}",
|
|
4536
4698
|
"services.configure": "配置",
|
|
4537
4699
|
"services.configureLabel": "配置 {name}",
|
|
4538
|
-
"services.off": "
|
|
4700
|
+
"services.off": "未启用",
|
|
4539
4701
|
"services.keyless": "无需密钥",
|
|
4540
4702
|
"services.personalKey": "个人密钥 {ref}",
|
|
4541
4703
|
"services.account": "DeepSeek 账号或 {ref}",
|
|
@@ -4741,15 +4903,15 @@ window.__ModuleLoader__.load({
|
|
|
4741
4903
|
document.head.appendChild(style);
|
|
4742
4904
|
}
|
|
4743
4905
|
var Section_module_css_default = {
|
|
4744
|
-
"container": "La6KHG_container",
|
|
4745
4906
|
"caption": "La6KHG_caption",
|
|
4907
|
+
"container": "La6KHG_container",
|
|
4746
4908
|
"segmented": "La6KHG_segmented",
|
|
4747
4909
|
"error": "La6KHG_error",
|
|
4748
4910
|
"label": "La6KHG_label"
|
|
4749
4911
|
};
|
|
4750
4912
|
//#endregion
|
|
4751
4913
|
//#region src/client/section.ts
|
|
4752
|
-
function searchSection(selection, settings, t) {
|
|
4914
|
+
function searchSection(selection, settings, remoteServicesOff, t) {
|
|
4753
4915
|
function Options({ sessionId }) {
|
|
4754
4916
|
const state = useObservable(selection.source(sessionId));
|
|
4755
4917
|
const [error, setError] = (0, react.useState)("");
|
|
@@ -4787,6 +4949,7 @@ window.__ModuleLoader__.load({
|
|
|
4787
4949
|
title: () => t("section.title"),
|
|
4788
4950
|
selection,
|
|
4789
4951
|
settings,
|
|
4952
|
+
remoteServicesOff,
|
|
4790
4953
|
Options,
|
|
4791
4954
|
describe: (connection) => describe(connection, t),
|
|
4792
4955
|
sourceText: (view) => sourceText(view, t),
|
|
@@ -4802,7 +4965,7 @@ window.__ModuleLoader__.load({
|
|
|
4802
4965
|
};
|
|
4803
4966
|
//#endregion
|
|
4804
4967
|
//#region \0dsh-css-module:/home/runner/work/dsh-tool-web-enhanced/dsh-tool-web-enhanced/packages/search-enhanced/src/client/settings/Settings.module.css.mjs
|
|
4805
|
-
const css = ".o9fCSq_page{min-width:0;color:var(--dsw-alias-label-primary);flex-direction:column;gap:28px;display:flex;container-type:inline-size}.o9fCSq_intro{color:var(--dsw-alias-label-secondary);margin:0;font-size:13px;line-height:20px}.o9fCSq_status{color:var(--dsw-alias-label-tertiary);align-items:center;gap:6px;margin:0;font-size:13px;line-height:20px;display:flex}.o9fCSq_warning{border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-module-platform);color:var(--dsw-alias-state-warn-label);margin:0;padding:8px 12px;font-size:12px;line-height:18px}.o9fCSq_section{flex-direction:column;gap:4px;min-width:0;display:flex}.o9fCSq_sectionHead{flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px;min-height:28px;display:flex}.o9fCSq_sectionTitle{margin:0;font-size:14px;font-weight:500;line-height:20px}.o9fCSq_sectionActions{flex-wrap:wrap;gap:4px;display:flex}.o9fCSq_hint,.o9fCSq_note{color:var(--dsw-alias-label-tertiary);margin:0;font-size:12px;line-height:18px}.o9fCSq_panel .o9fCSq_hint,.o9fCSq_editor .o9fCSq_hint{color:var(--dsw-alias-label-secondary)}.o9fCSq_hint [role=status]{color:var(--dsw-alias-label-secondary);align-items:baseline;gap:6px;margin-top:4px;display:flex}.o9fCSq_note{color:var(--dsw-alias-label-secondary)}.o9fCSq_error,.o9fCSq_success,.o9fCSq_fieldError{color:var(--dsw-alias-state-error-primary);margin:0;font-size:12px;line-height:18px}.o9fCSq_success{color:var(--dsw-alias-state-success-primary)}.o9fCSq_settingRow{border-bottom:.5px solid var(--dsw-alias-border-l2);flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px 24px;padding:14px 2px;display:flex}.o9fCSq_settingRow:last-of-type{border-bottom:0}.o9fCSq_settingText{flex-direction:column;flex:200px;gap:2px;min-width:0;display:flex}.o9fCSq_settingTitle{font-size:13.5px;font-weight:500;line-height:20px}.o9fCSq_settingControl{flex:0 auto;justify-content:flex-end;min-width:0;max-width:100%;display:flex}.o9fCSq_selectAnchor{min-width:0;max-width:100%}.o9fCSq_select,.o9fCSq_selectCompact{box-sizing:border-box;border-radius:var(--dsw-radius-md);min-width:0;max-width:100%;font:inherit;color:var(--dsw-alias-label-primary);cursor:pointer;border:none;align-items:center;gap:8px;font-size:13px;line-height:20px;display:inline-flex}.o9fCSq_select{background:var(--dsw-alias-bg-module-platform);height:36px;padding:0 12px 0 14px}.o9fCSq_selectCompact{border:.5px solid var(--dsw-alias-border-l4);background:var(--dsw-alias-bg-layer-1);justify-content:space-between;width:100%;height:36px;padding:0 10px 0 12px}.o9fCSq_select:hover:not(:disabled){background:var(--dsw-alias-interactive-bg-hover)}.o9fCSq_select:disabled,.o9fCSq_selectCompact:disabled{color:var(--dsw-alias-label-tertiary);cursor:default}.o9fCSq_select:focus-visible,.o9fCSq_selectCompact:focus-visible{outline:var(--dsw-focus-ring-width) solid var(--dsw-focus-ring-color,var(--dsw-alias-state-business-primary));outline-offset:1px}.o9fCSq_selectValue{text-overflow:ellipsis;white-space:nowrap;min-width:0;overflow:hidden}.o9fCSq_selectChevron{color:var(--dsw-alias-label-tertiary);flex:none}.o9fCSq_list{flex-direction:column;margin:0;padding:0;list-style:none;display:flex}.o9fCSq_row{border-bottom:.5px solid var(--dsw-alias-border-l2);padding:12px 2px}.o9fCSq_row:last-child{border-bottom:0}.o9fCSq_rowLine{align-items:center;gap:8px 12px;min-width:0;display:flex}.o9fCSq_rowMain{flex-direction:column;flex:1 1 0;gap:2px;min-width:0;display:flex}.o9fCSq_rowTitle{flex-wrap:wrap;align-items:center;gap:6px;font-size:13.5px;font-weight:500;line-height:20px;display:inline-flex}.o9fCSq_rowMeta{color:var(--dsw-alias-label-tertiary);overflow-wrap:anywhere;font-size:12px;line-height:18px}.o9fCSq_rowMeta code,.o9fCSq_optionKey{font-family:var(--dsw-font-mono,ui-monospace, SFMono-Regular, Menlo, monospace);font-size:11.5px}.o9fCSq_rowActions{box-sizing:border-box;flex-wrap:wrap;flex:none;align-items:center;gap:4px;display:flex}@container (width<=560px){.o9fCSq_rowLine:has(.o9fCSq_rowActions){flex-wrap:wrap}.o9fCSq_rowActions{flex-basis:100%;order:3;padding-left:10px}}.o9fCSq_segmented{align-self:flex-start;max-width:100%}.o9fCSq_disclosure{color:var(--dsw-alias-label-secondary)}.o9fCSq_disclosureIcon{flex:none;width:12px;height:12px;transition:transform .12s}.o9fCSq_disclosureOpen{transform:rotate(180deg)}@media (prefers-reduced-motion:reduce){.o9fCSq_disclosureIcon{transition:none}}.o9fCSq_danger{color:var(--dsw-alias-state-error-primary)}.o9fCSq_panel,.o9fCSq_editor{border-radius:var(--dsw-radius-lg);background:var(--dsw-alias-bg-module-platform);flex-direction:column;gap:16px;margin:12px 0 2px;padding:16px;display:flex}.o9fCSq_field,.o9fCSq_formField{flex-direction:column;gap:6px;min-width:0;display:flex}.o9fCSq_fieldHead{align-items:center;gap:8px;display:flex}.o9fCSq_fieldLabel{color:var(--dsw-alias-label-primary);font-size:13px;font-weight:500;line-height:20px}.o9fCSq_fieldState{color:var(--dsw-alias-label-tertiary);font-size:12px;line-height:18px}.o9fCSq_inline{flex-wrap:wrap;gap:8px;display:flex}.o9fCSq_inline>.o9fCSq_input{flex:160px}.o9fCSq_input{box-sizing:border-box;min-width:0;height:36px}.o9fCSq_input:has(input[aria-invalid=true]){border-color:var(--dsw-alias-state-error-primary)}.o9fCSq_link{color:var(--dsw-alias-link);align-self:flex-start;align-items:center;gap:2px;font-size:12px;font-weight:500;line-height:18px;text-decoration:none;display:inline-flex}.o9fCSq_link:hover,.o9fCSq_link:focus-visible{text-underline-offset:3px;text-decoration:underline dotted}.o9fCSq_optionGrid{grid-template-columns:repeat(auto-fill,minmax(min(100%,200px),1fr));gap:12px 16px;display:grid}.o9fCSq_option{flex-direction:column;gap:4px;min-width:0;display:flex}.o9fCSq_optionName{min-width:0;color:var(--dsw-alias-label-secondary);align-items:baseline;gap:6px;font-size:12px;line-height:18px;display:flex}.o9fCSq_optionKey{text-overflow:ellipsis;white-space:nowrap;color:var(--dsw-alias-label-tertiary);overflow:hidden}.o9fCSq_actions{flex-wrap:wrap;justify-content:flex-end;gap:8px;display:flex}.o9fCSq_empty{color:var(--dsw-alias-label-tertiary);margin:0;padding:8px 2px;font-size:13px;line-height:20px}.o9fCSq_editorTitle{margin:0;font-size:13.5px;font-weight:500;line-height:20px}.o9fCSq_formGrid{grid-template-columns:repeat(2,minmax(0,1fr));align-items:start;gap:14px 16px;display:grid}.o9fCSq_formWide{grid-column:1/-1}@container (width<=760px){.o9fCSq_optionGrid{grid-template-columns:repeat(2,minmax(0,1fr))}}@container (width<=480px){.o9fCSq_optionGrid{grid-template-columns:minmax(0,1fr)}.o9fCSq_settingControl{flex-basis:100%;justify-content:flex-start}.o9fCSq_panel{padding:12px}}@container (width<=520px){.o9fCSq_formGrid{grid-template-columns:minmax(0,1fr)}}.o9fCSq_prefixed{box-sizing:border-box;border:.5px solid var(--dsw-alias-border-l4);border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-layer-1);align-items:center;height:36px;padding:0 8px 0 10px;display:flex}.o9fCSq_prefixed:focus-within{border-color:var(--dsw-alias-state-business-primary)}.o9fCSq_prefixedDisabled{color:var(--dsw-alias-label-tertiary)}.o9fCSq_prefix{font-family:var(--dsw-font-mono,ui-monospace, SFMono-Regular, Menlo, monospace);color:var(--dsw-alias-label-tertiary);flex:none;font-size:13px;line-height:22px}.o9fCSq_prefixedInput{min-width:0;font:inherit;color:var(--dsw-alias-label-primary);background:0 0;border:none;outline:none;flex:1;padding:0;font-size:14px;line-height:22px}.o9fCSq_prefixedInput::placeholder{color:var(--dsw-alias-label-dimmed)}.o9fCSq_reset{border-top:.5px solid var(--dsw-alias-border-l2);flex-direction:column;gap:6px;padding-top:16px;display:flex}.o9fCSq_confirmRow{flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px 24px;display:flex}.o9fCSq_row .o9fCSq_confirmRow{border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-module-platform);margin-top:10px;padding:8px 12px}.o9fCSq_confirmText{min-width:0;color:var(--dsw-alias-label-secondary);flex:240px;font-size:12px;line-height:18px}.o9fCSq_optionWide{grid-column:1/-1}.o9fCSq_textarea{box-sizing:border-box;resize:vertical;border:.5px solid var(--dsw-alias-border-l4);border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-layer-1);width:100%;min-width:0;min-height:72px;color:var(--dsw-alias-label-primary);font-family:var(--dsw-font-mono,ui-monospace, SFMono-Regular, Menlo, monospace);padding:8px 10px;font-size:12px;line-height:20px}.o9fCSq_textarea:focus{border-color:var(--dsw-alias-state-business-primary);outline:none}.o9fCSq_textarea::placeholder{color:var(--dsw-alias-label-dimmed)}.o9fCSq_textarea[aria-invalid=true]{border-color:var(--dsw-alias-state-error-primary)}.o9fCSq_textarea:disabled{cursor:not-allowed;opacity:.5}.o9fCSq_optionGroup{border-top:.5px solid var(--dsw-alias-border-l4);flex-direction:column;gap:8px;padding-top:12px;display:flex}.o9fCSq_optionGroup:first-child,.o9fCSq_fieldHead+.o9fCSq_optionGroup{border-top:0;padding-top:0}.o9fCSq_optionGroupTitle{color:var(--dsw-alias-label-primary);font-size:12px;font-weight:500;line-height:18px}.o9fCSq_trust{border:.5px solid var(--dsw-alias-state-warn-primary);border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-layer-1);padding:10px 12px}.o9fCSq_trust .o9fCSq_trustCheck{align-items:flex-start}.o9fCSq_trust .o9fCSq_trustCheck input{margin-top:2px}.o9fCSq_actions>.o9fCSq_hint{flex:auto;align-self:center}";
|
|
4968
|
+
const css = ".o9fCSq_page{min-width:0;color:var(--dsw-alias-label-primary);flex-direction:column;gap:28px;display:flex;container-type:inline-size}.o9fCSq_intro{color:var(--dsw-alias-label-secondary);margin:0;font-size:13px;line-height:20px}.o9fCSq_status{color:var(--dsw-alias-label-tertiary);align-items:center;gap:6px;margin:0;font-size:13px;line-height:20px;display:flex}.o9fCSq_warning{border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-module-platform);color:var(--dsw-alias-state-warn-label);margin:0;padding:8px 12px;font-size:12px;line-height:18px}.o9fCSq_section{flex-direction:column;gap:4px;min-width:0;display:flex}.o9fCSq_sectionHead{flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px;min-height:28px;display:flex}.o9fCSq_sectionTitle{margin:0;font-size:14px;font-weight:500;line-height:20px}.o9fCSq_sectionActions{flex-wrap:wrap;gap:4px;display:flex}.o9fCSq_hint,.o9fCSq_note{color:var(--dsw-alias-label-tertiary);margin:0;font-size:12px;line-height:18px}.o9fCSq_panel .o9fCSq_hint,.o9fCSq_editor .o9fCSq_hint{color:var(--dsw-alias-label-secondary)}.o9fCSq_hint [role=status]{color:var(--dsw-alias-label-secondary);align-items:baseline;gap:6px;margin-top:4px;display:flex}.o9fCSq_note{color:var(--dsw-alias-label-secondary)}.o9fCSq_error,.o9fCSq_success,.o9fCSq_fieldError{color:var(--dsw-alias-state-error-primary);margin:0;font-size:12px;line-height:18px}.o9fCSq_success{color:var(--dsw-alias-state-success-primary)}.o9fCSq_settingRow{border-bottom:.5px solid var(--dsw-alias-border-l2);flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px 24px;padding:14px 2px;display:flex}.o9fCSq_settingRow:last-of-type{border-bottom:0}.o9fCSq_settingText{flex-direction:column;flex:200px;gap:2px;min-width:0;display:flex}.o9fCSq_settingTitle{font-size:13.5px;font-weight:500;line-height:20px}.o9fCSq_settingLead{color:var(--dsw-alias-label-primary);margin:0;font-size:13px;font-weight:400;line-height:20px}.o9fCSq_settingControl{flex:0 auto;justify-content:flex-end;min-width:0;max-width:100%;display:flex}.o9fCSq_selectAnchor{min-width:0;max-width:100%}.o9fCSq_select,.o9fCSq_selectCompact{box-sizing:border-box;border-radius:var(--dsw-radius-md);min-width:0;max-width:100%;font:inherit;color:var(--dsw-alias-label-primary);cursor:pointer;border:none;align-items:center;gap:8px;font-size:13px;line-height:20px;display:inline-flex}.o9fCSq_select{background:var(--dsw-alias-bg-module-platform);height:36px;padding:0 12px 0 14px}.o9fCSq_selectCompact{border:.5px solid var(--dsw-alias-border-l4);background:var(--dsw-alias-bg-layer-1);justify-content:space-between;width:100%;height:36px;padding:0 10px 0 12px}.o9fCSq_select:hover:not(:disabled){background:var(--dsw-alias-interactive-bg-hover)}.o9fCSq_select:disabled,.o9fCSq_selectCompact:disabled{color:var(--dsw-alias-label-tertiary);cursor:default}.o9fCSq_select:focus-visible,.o9fCSq_selectCompact:focus-visible{outline:var(--dsw-focus-ring-width) solid var(--dsw-focus-ring-color,var(--dsw-alias-state-business-primary));outline-offset:1px}.o9fCSq_selectValue{text-overflow:ellipsis;white-space:nowrap;min-width:0;overflow:hidden}.o9fCSq_selectChevron{color:var(--dsw-alias-label-tertiary);flex:none}.o9fCSq_list{flex-direction:column;margin:0;padding:0;list-style:none;display:flex}.o9fCSq_row{border-bottom:.5px solid var(--dsw-alias-border-l2);padding:12px 2px}.o9fCSq_row:last-child{border-bottom:0}.o9fCSq_rowLine{align-items:center;gap:8px 12px;min-width:0;display:flex}.o9fCSq_rowMain{flex-direction:column;flex:1 1 0;gap:2px;min-width:0;display:flex}.o9fCSq_rowTitle{flex-wrap:wrap;align-items:center;gap:6px;font-size:13.5px;font-weight:500;line-height:20px;display:inline-flex}.o9fCSq_rowMeta{color:var(--dsw-alias-label-tertiary);overflow-wrap:anywhere;font-size:12px;line-height:18px}.o9fCSq_rowMeta code,.o9fCSq_optionKey{font-family:var(--dsw-font-mono,ui-monospace, SFMono-Regular, Menlo, monospace);font-size:11.5px}.o9fCSq_rowActions{box-sizing:border-box;flex-wrap:wrap;flex:none;align-items:center;gap:4px;display:flex}@container (width<=560px){.o9fCSq_rowLine:has(.o9fCSq_rowActions){flex-wrap:wrap}.o9fCSq_rowActions{flex-basis:100%;order:3;padding-left:10px}}.o9fCSq_segmented{align-self:flex-start;max-width:100%}.o9fCSq_disclosure{color:var(--dsw-alias-label-secondary)}.o9fCSq_disclosureIcon{flex:none;width:12px;height:12px;transition:transform .12s}.o9fCSq_disclosureOpen{transform:rotate(180deg)}@media (prefers-reduced-motion:reduce){.o9fCSq_disclosureIcon{transition:none}}.o9fCSq_danger{color:var(--dsw-alias-state-error-primary)}.o9fCSq_panel,.o9fCSq_editor{border-radius:var(--dsw-radius-lg);background:var(--dsw-alias-bg-module-platform);flex-direction:column;gap:16px;margin:12px 0 2px;padding:16px;display:flex}.o9fCSq_field,.o9fCSq_formField{flex-direction:column;gap:6px;min-width:0;display:flex}.o9fCSq_fieldHead{align-items:center;gap:8px;display:flex}.o9fCSq_fieldLabel{color:var(--dsw-alias-label-primary);font-size:13px;font-weight:500;line-height:20px}.o9fCSq_fieldState{color:var(--dsw-alias-label-tertiary);font-size:12px;line-height:18px}.o9fCSq_inline{flex-wrap:wrap;gap:8px;display:flex}.o9fCSq_inline>.o9fCSq_input{flex:160px}.o9fCSq_input{box-sizing:border-box;min-width:0;height:36px}.o9fCSq_input:has(input[aria-invalid=true]){border-color:var(--dsw-alias-state-error-primary)}.o9fCSq_link{color:var(--dsw-alias-link);align-self:flex-start;align-items:center;gap:2px;font-size:12px;font-weight:500;line-height:18px;text-decoration:none;display:inline-flex}.o9fCSq_link:hover,.o9fCSq_link:focus-visible{text-underline-offset:3px;text-decoration:underline dotted}.o9fCSq_optionGrid{grid-template-columns:repeat(auto-fill,minmax(min(100%,200px),1fr));gap:12px 16px;display:grid}.o9fCSq_option{flex-direction:column;gap:4px;min-width:0;display:flex}.o9fCSq_optionName{min-width:0;color:var(--dsw-alias-label-secondary);align-items:baseline;gap:6px;font-size:12px;line-height:18px;display:flex}.o9fCSq_optionKey{text-overflow:ellipsis;white-space:nowrap;color:var(--dsw-alias-label-tertiary);overflow:hidden}.o9fCSq_actions{flex-wrap:wrap;justify-content:flex-end;gap:8px;display:flex}.o9fCSq_empty{color:var(--dsw-alias-label-tertiary);margin:0;padding:8px 2px;font-size:13px;line-height:20px}.o9fCSq_editorTitle{margin:0;font-size:13.5px;font-weight:500;line-height:20px}.o9fCSq_formGrid{grid-template-columns:repeat(2,minmax(0,1fr));align-items:start;gap:14px 16px;display:grid}.o9fCSq_formWide{grid-column:1/-1}@container (width<=760px){.o9fCSq_optionGrid{grid-template-columns:repeat(2,minmax(0,1fr))}}@container (width<=480px){.o9fCSq_optionGrid{grid-template-columns:minmax(0,1fr)}.o9fCSq_settingControl{flex-basis:100%;justify-content:flex-start}.o9fCSq_panel{padding:12px}}@container (width<=520px){.o9fCSq_formGrid{grid-template-columns:minmax(0,1fr)}}.o9fCSq_prefixed{box-sizing:border-box;border:.5px solid var(--dsw-alias-border-l4);border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-layer-1);align-items:center;height:36px;padding:0 8px 0 10px;display:flex}.o9fCSq_prefixed:focus-within{border-color:var(--dsw-alias-state-business-primary)}.o9fCSq_prefixedDisabled{color:var(--dsw-alias-label-tertiary)}.o9fCSq_prefix{font-family:var(--dsw-font-mono,ui-monospace, SFMono-Regular, Menlo, monospace);color:var(--dsw-alias-label-tertiary);flex:none;font-size:13px;line-height:22px}.o9fCSq_prefixedInput{min-width:0;font:inherit;color:var(--dsw-alias-label-primary);background:0 0;border:none;outline:none;flex:1;padding:0;font-size:14px;line-height:22px}.o9fCSq_prefixedInput::placeholder{color:var(--dsw-alias-label-dimmed)}.o9fCSq_reset{border-top:.5px solid var(--dsw-alias-border-l2);flex-direction:column;gap:6px;padding-top:16px;display:flex}.o9fCSq_confirmRow{flex-wrap:wrap;justify-content:space-between;align-items:center;gap:8px 24px;display:flex}.o9fCSq_row .o9fCSq_confirmRow{border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-module-platform);margin-top:10px;padding:8px 12px}.o9fCSq_confirmText{min-width:0;color:var(--dsw-alias-label-secondary);flex:240px;font-size:12px;line-height:18px}.o9fCSq_optionWide{grid-column:1/-1}.o9fCSq_textarea{box-sizing:border-box;resize:vertical;border:.5px solid var(--dsw-alias-border-l4);border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-layer-1);width:100%;min-width:0;min-height:72px;color:var(--dsw-alias-label-primary);font-family:var(--dsw-font-mono,ui-monospace, SFMono-Regular, Menlo, monospace);padding:8px 10px;font-size:12px;line-height:20px}.o9fCSq_textarea:focus{border-color:var(--dsw-alias-state-business-primary);outline:none}.o9fCSq_textarea::placeholder{color:var(--dsw-alias-label-dimmed)}.o9fCSq_textarea[aria-invalid=true]{border-color:var(--dsw-alias-state-error-primary)}.o9fCSq_textarea:disabled{cursor:not-allowed;opacity:.5}.o9fCSq_optionGroup{border-top:.5px solid var(--dsw-alias-border-l4);flex-direction:column;gap:8px;padding-top:12px;display:flex}.o9fCSq_optionGroup:first-child,.o9fCSq_fieldHead+.o9fCSq_optionGroup{border-top:0;padding-top:0}.o9fCSq_optionGroupTitle{color:var(--dsw-alias-label-primary);font-size:12px;font-weight:500;line-height:18px}.o9fCSq_trust{border:.5px solid var(--dsw-alias-state-warn-primary);border-radius:var(--dsw-radius-md);background:var(--dsw-alias-bg-layer-1);padding:10px 12px}.o9fCSq_trust .o9fCSq_trustCheck{align-items:flex-start}.o9fCSq_trust .o9fCSq_trustCheck input{margin-top:2px}.o9fCSq_actions>.o9fCSq_hint{flex:auto;align-self:center}";
|
|
4806
4969
|
if (typeof document !== "undefined" && document.querySelector("style[data-plugin-css=" + JSON.stringify("dsh-web-search-enhanced/src/client/settings/Settings.module.css") + "]") === null) {
|
|
4807
4970
|
const style = document.createElement("style");
|
|
4808
4971
|
style.dataset.plugin = "dsh-web-search-enhanced";
|
|
@@ -4811,72 +4974,73 @@ window.__ModuleLoader__.load({
|
|
|
4811
4974
|
document.head.appendChild(style);
|
|
4812
4975
|
}
|
|
4813
4976
|
var Settings_module_css_default = {
|
|
4814
|
-
"
|
|
4815
|
-
"
|
|
4977
|
+
"optionGroup": "o9fCSq_optionGroup",
|
|
4978
|
+
"selectCompact": "o9fCSq_selectCompact",
|
|
4816
4979
|
"hint": "o9fCSq_hint",
|
|
4817
|
-
"rowMain": "o9fCSq_rowMain",
|
|
4818
|
-
"optionGroupTitle": "o9fCSq_optionGroupTitle",
|
|
4819
|
-
"warning": "o9fCSq_warning",
|
|
4820
|
-
"list": "o9fCSq_list",
|
|
4821
4980
|
"actions": "o9fCSq_actions",
|
|
4981
|
+
"editorTitle": "o9fCSq_editorTitle",
|
|
4982
|
+
"section": "o9fCSq_section",
|
|
4983
|
+
"prefix": "o9fCSq_prefix",
|
|
4984
|
+
"error": "o9fCSq_error",
|
|
4985
|
+
"disclosure": "o9fCSq_disclosure",
|
|
4986
|
+
"fieldHead": "o9fCSq_fieldHead",
|
|
4987
|
+
"page": "o9fCSq_page",
|
|
4988
|
+
"rowActions": "o9fCSq_rowActions",
|
|
4989
|
+
"segmented": "o9fCSq_segmented",
|
|
4990
|
+
"settingLead": "o9fCSq_settingLead",
|
|
4991
|
+
"optionGroupTitle": "o9fCSq_optionGroupTitle",
|
|
4992
|
+
"rowTitle": "o9fCSq_rowTitle",
|
|
4993
|
+
"formField": "o9fCSq_formField",
|
|
4994
|
+
"intro": "o9fCSq_intro",
|
|
4995
|
+
"settingText": "o9fCSq_settingText",
|
|
4996
|
+
"prefixedDisabled": "o9fCSq_prefixedDisabled",
|
|
4997
|
+
"settingControl": "o9fCSq_settingControl",
|
|
4822
4998
|
"trustCheck": "o9fCSq_trustCheck",
|
|
4999
|
+
"prefixed": "o9fCSq_prefixed",
|
|
5000
|
+
"sectionHead": "o9fCSq_sectionHead",
|
|
5001
|
+
"select": "o9fCSq_select",
|
|
5002
|
+
"fieldError": "o9fCSq_fieldError",
|
|
5003
|
+
"inline": "o9fCSq_inline",
|
|
5004
|
+
"link": "o9fCSq_link",
|
|
5005
|
+
"field": "o9fCSq_field",
|
|
5006
|
+
"option": "o9fCSq_option",
|
|
5007
|
+
"textarea": "o9fCSq_textarea",
|
|
5008
|
+
"sectionActions": "o9fCSq_sectionActions",
|
|
5009
|
+
"sectionTitle": "o9fCSq_sectionTitle",
|
|
5010
|
+
"rowMeta": "o9fCSq_rowMeta",
|
|
5011
|
+
"empty": "o9fCSq_empty",
|
|
4823
5012
|
"fieldState": "o9fCSq_fieldState",
|
|
4824
5013
|
"row": "o9fCSq_row",
|
|
5014
|
+
"note": "o9fCSq_note",
|
|
5015
|
+
"settingRow": "o9fCSq_settingRow",
|
|
4825
5016
|
"selectChevron": "o9fCSq_selectChevron",
|
|
4826
|
-
"
|
|
4827
|
-
"
|
|
4828
|
-
"formGrid": "o9fCSq_formGrid",
|
|
5017
|
+
"list": "o9fCSq_list",
|
|
5018
|
+
"trust": "o9fCSq_trust",
|
|
4829
5019
|
"status": "o9fCSq_status",
|
|
4830
|
-
"
|
|
5020
|
+
"input": "o9fCSq_input",
|
|
5021
|
+
"confirmRow": "o9fCSq_confirmRow",
|
|
5022
|
+
"fieldLabel": "o9fCSq_fieldLabel",
|
|
5023
|
+
"danger": "o9fCSq_danger",
|
|
5024
|
+
"formGrid": "o9fCSq_formGrid",
|
|
4831
5025
|
"selectAnchor": "o9fCSq_selectAnchor",
|
|
4832
|
-
"
|
|
4833
|
-
"editor": "o9fCSq_editor",
|
|
4834
|
-
"trust": "o9fCSq_trust",
|
|
4835
|
-
"settingTitle": "o9fCSq_settingTitle",
|
|
5026
|
+
"formWide": "o9fCSq_formWide",
|
|
4836
5027
|
"success": "o9fCSq_success",
|
|
4837
|
-
"
|
|
4838
|
-
"
|
|
4839
|
-
"
|
|
4840
|
-
"rowMeta": "o9fCSq_rowMeta",
|
|
4841
|
-
"optionGrid": "o9fCSq_optionGrid",
|
|
4842
|
-
"sectionTitle": "o9fCSq_sectionTitle",
|
|
4843
|
-
"input": "o9fCSq_input",
|
|
4844
|
-
"prefixedInput": "o9fCSq_prefixedInput",
|
|
5028
|
+
"editor": "o9fCSq_editor",
|
|
5029
|
+
"panel": "o9fCSq_panel",
|
|
5030
|
+
"disclosureOpen": "o9fCSq_disclosureOpen",
|
|
4845
5031
|
"reset": "o9fCSq_reset",
|
|
4846
|
-
"
|
|
4847
|
-
"
|
|
4848
|
-
"page": "o9fCSq_page",
|
|
4849
|
-
"link": "o9fCSq_link",
|
|
4850
|
-
"error": "o9fCSq_error",
|
|
4851
|
-
"editorTitle": "o9fCSq_editorTitle",
|
|
4852
|
-
"disclosure": "o9fCSq_disclosure",
|
|
5032
|
+
"prefixedInput": "o9fCSq_prefixedInput",
|
|
5033
|
+
"optionKey": "o9fCSq_optionKey",
|
|
4853
5034
|
"optionName": "o9fCSq_optionName",
|
|
4854
|
-
"settingText": "o9fCSq_settingText",
|
|
4855
|
-
"segmented": "o9fCSq_segmented",
|
|
4856
|
-
"danger": "o9fCSq_danger",
|
|
4857
|
-
"sectionActions": "o9fCSq_sectionActions",
|
|
4858
|
-
"settingControl": "o9fCSq_settingControl",
|
|
4859
|
-
"select": "o9fCSq_select",
|
|
4860
5035
|
"selectValue": "o9fCSq_selectValue",
|
|
5036
|
+
"rowMain": "o9fCSq_rowMain",
|
|
5037
|
+
"confirmText": "o9fCSq_confirmText",
|
|
5038
|
+
"optionWide": "o9fCSq_optionWide",
|
|
5039
|
+
"warning": "o9fCSq_warning",
|
|
5040
|
+
"settingTitle": "o9fCSq_settingTitle",
|
|
4861
5041
|
"rowLine": "o9fCSq_rowLine",
|
|
4862
|
-
"
|
|
4863
|
-
"
|
|
4864
|
-
"prefix": "o9fCSq_prefix",
|
|
4865
|
-
"empty": "o9fCSq_empty",
|
|
4866
|
-
"sectionHead": "o9fCSq_sectionHead",
|
|
4867
|
-
"disclosureIcon": "o9fCSq_disclosureIcon",
|
|
4868
|
-
"settingRow": "o9fCSq_settingRow",
|
|
4869
|
-
"fieldLabel": "o9fCSq_fieldLabel",
|
|
4870
|
-
"field": "o9fCSq_field",
|
|
4871
|
-
"section": "o9fCSq_section",
|
|
4872
|
-
"fieldHead": "o9fCSq_fieldHead",
|
|
4873
|
-
"optionGroup": "o9fCSq_optionGroup",
|
|
4874
|
-
"rowActions": "o9fCSq_rowActions",
|
|
4875
|
-
"note": "o9fCSq_note",
|
|
4876
|
-
"formWide": "o9fCSq_formWide",
|
|
4877
|
-
"prefixedDisabled": "o9fCSq_prefixedDisabled",
|
|
4878
|
-
"rowTitle": "o9fCSq_rowTitle",
|
|
4879
|
-
"selectCompact": "o9fCSq_selectCompact"
|
|
5042
|
+
"optionGrid": "o9fCSq_optionGrid",
|
|
5043
|
+
"disclosureIcon": "o9fCSq_disclosureIcon"
|
|
4880
5044
|
};
|
|
4881
5045
|
//#endregion
|
|
4882
5046
|
//#region src/client/settings/CredentialEditor.tsx
|
|
@@ -5317,6 +5481,18 @@ window.__ModuleLoader__.load({
|
|
|
5317
5481
|
});
|
|
5318
5482
|
}
|
|
5319
5483
|
//#endregion
|
|
5484
|
+
//#region src/client/settings/EnhancedToolsSection.tsx
|
|
5485
|
+
const EnhancedToolsSection = createEnhancedToolsSection({
|
|
5486
|
+
classes: Settings_module_css_default,
|
|
5487
|
+
parts: settingsParts,
|
|
5488
|
+
sparse: sparse_exports,
|
|
5489
|
+
keys: {
|
|
5490
|
+
title: "enhanced.title",
|
|
5491
|
+
description: "enhanced.description",
|
|
5492
|
+
consent: "enhanced.consent"
|
|
5493
|
+
}
|
|
5494
|
+
});
|
|
5495
|
+
//#endregion
|
|
5320
5496
|
//#region src/client/settings/PairingsSection.tsx
|
|
5321
5497
|
const PairingsSection = createPairingsSection({
|
|
5322
5498
|
classes: Settings_module_css_default,
|
|
@@ -5350,6 +5526,7 @@ window.__ModuleLoader__.load({
|
|
|
5350
5526
|
optionGroups: { "session-model": SESSION_MODEL_GROUPS },
|
|
5351
5527
|
keys: {
|
|
5352
5528
|
"services.title": "services.title",
|
|
5529
|
+
"services.optInNotice": "services.optInNotice",
|
|
5353
5530
|
"options.hint": "options.hint",
|
|
5354
5531
|
"options.keylessMore": "options.keylessMore",
|
|
5355
5532
|
"options.invalid": "options.invalid",
|
|
@@ -5385,12 +5562,12 @@ window.__ModuleLoader__.load({
|
|
|
5385
5562
|
* Controls write immediately as sparse operations against the revision the
|
|
5386
5563
|
* page shows; credentials go to DSH Credentials only.
|
|
5387
5564
|
*/
|
|
5388
|
-
function SettingsPage({ useSettings, useCredentials, useRoute, usePairings, mutate, saveCredential, forgetPairing, t }) {
|
|
5565
|
+
function SettingsPage({ useSettings, useCredentials, useRoute, usePairings, readSettings, mutate, saveCredential, forgetPairing, t }) {
|
|
5389
5566
|
const snapshot = useSettings((value) => value);
|
|
5390
5567
|
const credentials = useCredentials((value) => value);
|
|
5391
5568
|
const route = useRoute((value) => value);
|
|
5392
5569
|
const pairings = usePairings((value) => value);
|
|
5393
|
-
const { view, write, migrationError } = useSettingsDocument(snapshot, resolveSettings, mutate);
|
|
5570
|
+
const { view, write, migrationError } = useSettingsDocument(snapshot, readSettings, resolveSettings, mutate);
|
|
5394
5571
|
if (snapshot.status === "unavailable") return null;
|
|
5395
5572
|
if (snapshot.value === void 0 || snapshot.revision === void 0) return /* @__PURE__ */ (0, react_jsx_runtime.jsxs)("p", {
|
|
5396
5573
|
className: Settings_module_css_default.status,
|
|
@@ -5455,6 +5632,11 @@ window.__ModuleLoader__.load({
|
|
|
5455
5632
|
credentials,
|
|
5456
5633
|
t
|
|
5457
5634
|
}),
|
|
5635
|
+
/* @__PURE__ */ (0, react_jsx_runtime.jsx)(EnhancedToolsSection, {
|
|
5636
|
+
doc,
|
|
5637
|
+
write,
|
|
5638
|
+
t
|
|
5639
|
+
}),
|
|
5458
5640
|
/* @__PURE__ */ (0, react_jsx_runtime.jsx)(ServicesSection, {
|
|
5459
5641
|
doc,
|
|
5460
5642
|
write,
|
|
@@ -5554,6 +5736,7 @@ window.__ModuleLoader__.load({
|
|
|
5554
5736
|
route: route.source,
|
|
5555
5737
|
pairings: pairings.source
|
|
5556
5738
|
},
|
|
5739
|
+
readSettings: () => settings.getSnapshot(),
|
|
5557
5740
|
async mutate(ops, revision) {
|
|
5558
5741
|
return settings.mutate(ops, revision);
|
|
5559
5742
|
},
|
|
@@ -5572,7 +5755,7 @@ window.__ModuleLoader__.load({
|
|
|
5572
5755
|
locale: NS,
|
|
5573
5756
|
inject: () => page
|
|
5574
5757
|
}, SettingsPage))), "search: settings page");
|
|
5575
|
-
const section = searchSection(selection, navigation, t);
|
|
5758
|
+
const section = searchSection(selection, navigation, remoteServicesOffSource(settings, CATALOG, resolveSettings), t);
|
|
5576
5759
|
scope.inject(["webConnections"], (ui) => {
|
|
5577
5760
|
ui.effect(() => ui.webConnections.registerRoute("search", route), "search: route facts");
|
|
5578
5761
|
ui.effect(() => {
|