@xmanrui/dsh-im 4.24.0 → 4.24.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/lib/client.js CHANGED
@@ -595,7 +595,7 @@ var React33 = __toESM(require("react"), 1);
595
595
  // package.json
596
596
  var package_default = {
597
597
  name: "@xmanrui/dsh-im",
598
- version: "4.24.0",
598
+ version: "4.24.1",
599
599
  description: "\u628A\u5341\u4E00\u79CD IM \u6E20\u9053\u548C\u516C\u7F51 AI Office \u63A5\u5165\u672C\u673A DeepSeek Harness\u3002 Connect eleven IM channels and a public AI Office to a local DeepSeek Harness.",
600
600
  keywords: [
601
601
  "deepseek-harness",
@@ -675,6 +675,10 @@ var package_default = {
675
675
  {
676
676
  name: "wings1848",
677
677
  url: "https://github.com/wings1848"
678
+ },
679
+ {
680
+ name: "Zhe (Phil) Yang",
681
+ url: "https://github.com/yangzhe1991"
678
682
  }
679
683
  ],
680
684
  license: "MIT",
@@ -1232,6 +1236,8 @@ var EN = Object.freeze({
1232
1236
  "IM\u673A\u5668\u4EBA\u8BBE\u7F6E": "IM bot settings",
1233
1237
  "IM \u9762\u677F\u52A0\u8F7D\u5931\u8D25": "Could not load the IM panel",
1234
1238
  "\u66F4\u591A\u673A\u5668\u4EBA\u8BBE\u7F6E": "More bot settings",
1239
+ "\u66F4\u591A\u8BBE\u7F6E": "More settings",
1240
+ "\u5E38\u7528\u914D\u7F6E": "Common settings",
1235
1241
  "\u673A\u5668\u4EBA\u8BBE\u7F6E": "Bot settings",
1236
1242
  "\u673A\u5668\u4EBA\u8BBE\u7F6E\u9875\u7B7E": "Bot settings tabs",
1237
1243
  "\u6295\u9012\u8BBE\u7F6E": "Delivery settings",
@@ -1317,6 +1323,8 @@ var EN = Object.freeze({
1317
1323
  "\u5DF2\u5B89\u88C5\u7248\u672C": "Installed version",
1318
1324
  "\u76EE\u6807 profile": "Target profile",
1319
1325
  "\u76EE\u6807\u7248\u672C": "Target version",
1326
+ "\u6700\u65B0\u7248\u672C": "Latest version",
1327
+ "\u4E0A\u6B21\u66F4\u65B0\u76EE\u6807": "Previous update target",
1320
1328
  "\u65E0\u6CD5\u786E\u8BA4": "Unknown",
1321
1329
  "\u53D1\u73B0\u65B0\u7248\u672C": "Update available",
1322
1330
  "\u5DF2\u662F\u6700\u65B0\u7248\u672C": "Up to date",
@@ -1330,6 +1338,7 @@ var EN = Object.freeze({
1330
1338
  "\u66F4\u65B0\u5DF2\u751F\u6548": "Updated version is active",
1331
1339
  "\u66F4\u65B0\u5931\u8D25": "Update failed",
1332
1340
  "\u66F4\u65B0\u8BF7\u6C42\u5931\u8D25": "Update request failed",
1341
+ "\u6682\u65F6\u65E0\u6CD5\u5B89\u88C5\u66F4\u65B0": "Update installation is unavailable",
1333
1342
  "\u4EC5\u66F4\u65B0 DSH-IM\u3002\u5B89\u88C5\u5B8C\u6210\u540E\u9700\u624B\u52A8\u91CD\u542F\u540E\u53F0\uFF1B\u672C\u529F\u80FD\u4E0D\u4F1A\u81EA\u52A8\u91CD\u542F\u6216\u4E3B\u52A8\u5237\u65B0\u9875\u9762\u3002": "Only DSH-IM will be updated. Restart the backend manually after installation. This feature does not automatically restart it or initiate a page refresh.",
1334
1343
  "\u5F53\u524D\u662F\u6E90\u7801\u6216\u94FE\u63A5\u5B89\u88C5\uFF0C\u53EA\u80FD\u68C0\u67E5\u7248\u672C\uFF1B\u8BF7\u624B\u52A8\u66F4\u65B0\u6E90\u7801\uFF0C\u6216\u8FC1\u79FB\u5230 npm \u5B89\u88C5\u3002": "This is a source or linked installation. You can check versions, but must update the source manually or migrate to an npm installation.",
1335
1344
  "\u65E0\u6CD5\u786E\u8BA4\u5F53\u524D profile\uFF0C\u8BF7\u5728\u5BF9\u5E94\u7684 Harness \u73AF\u5883\u4E2D\u624B\u52A8\u66F4\u65B0\u3002": "The current profile could not be identified. Update manually in the corresponding Harness environment.",
@@ -4117,9 +4126,206 @@ function CredentialBindingPanel({
4117
4126
  }
4118
4127
 
4119
4128
  // plugin-src/client/channels/shared/collapsible-account.js
4129
+ var React9 = __toESM(require("react"), 1);
4130
+
4131
+ // plugin-src/client/channel-card-meta.js
4120
4132
  var React8 = __toESM(require("react"), 1);
4133
+ var BotSettingsContext = React8.createContext(Object.freeze({
4134
+ openBotSettings() {
4135
+ }
4136
+ }));
4137
+ function SettingsGlyph() {
4138
+ return h2(
4139
+ "svg",
4140
+ {
4141
+ viewBox: "0 0 24 24",
4142
+ width: 16,
4143
+ height: 16,
4144
+ fill: "none",
4145
+ stroke: "currentColor",
4146
+ strokeWidth: 1.8,
4147
+ strokeLinecap: "round",
4148
+ strokeLinejoin: "round",
4149
+ "aria-hidden": "true"
4150
+ },
4151
+ h2("circle", { cx: 12, cy: 12, r: 3 }),
4152
+ h2("path", { d: "M19.4 15a1.7 1.7 0 0 0 .34 1.88l.06.06-2.83 2.83-.06-.06a1.7 1.7 0 0 0-1.88-.34 1.7 1.7 0 0 0-1.03 1.55V21h-4v-.08A1.7 1.7 0 0 0 8.97 19.4a1.7 1.7 0 0 0-1.88.34l-.06.06-2.83-2.83.06-.06A1.7 1.7 0 0 0 4.6 15a1.7 1.7 0 0 0-1.52-1.03H3v-4h.08A1.7 1.7 0 0 0 4.6 8.97a1.7 1.7 0 0 0-.34-1.88l-.06-.06L7.03 4.2l.06.06a1.7 1.7 0 0 0 1.88.34A1.7 1.7 0 0 0 10 3.08V3h4v.08a1.7 1.7 0 0 0 1.03 1.52 1.7 1.7 0 0 0 1.88-.34l.06-.06 2.83 2.83-.06.06a1.7 1.7 0 0 0-.34 1.88A1.7 1.7 0 0 0 20.92 10H21v4h-.08A1.7 1.7 0 0 0 19.4 15Z" })
4153
+ );
4154
+ }
4155
+ function BotSettingsButton({
4156
+ channel: channel6,
4157
+ botId,
4158
+ botName,
4159
+ connected,
4160
+ accessPolicy,
4161
+ channelSettings
4162
+ }) {
4163
+ const { openBotSettings } = React8.useContext(BotSettingsContext);
4164
+ return h2(
4165
+ "span",
4166
+ { className: "dim-botSettingsAction" },
4167
+ h2(
4168
+ "button",
4169
+ {
4170
+ type: "button",
4171
+ className: "dim-botSettingsButton",
4172
+ "data-delivery-channel": channel6,
4173
+ "aria-label": "\u66F4\u591A\u673A\u5668\u4EBA\u8BBE\u7F6E",
4174
+ onClick: () => openBotSettings?.({
4175
+ ...channelSettings && typeof channelSettings === "object" ? channelSettings : {},
4176
+ channel: channel6,
4177
+ botId,
4178
+ botName,
4179
+ connected: Boolean(connected),
4180
+ accessPolicy
4181
+ })
4182
+ },
4183
+ h2(SettingsGlyph),
4184
+ h2("span", null, "\u66F4\u591A\u8BBE\u7F6E"),
4185
+ h2("span", { className: "dim-moreSettingsChevron", "aria-hidden": "true" })
4186
+ )
4187
+ );
4188
+ }
4189
+ function messageErrorTime(value) {
4190
+ try {
4191
+ return new Intl.DateTimeFormat(isEnglish() ? "en-US" : "zh-CN", {
4192
+ year: "numeric",
4193
+ month: "2-digit",
4194
+ day: "2-digit",
4195
+ hour: "2-digit",
4196
+ minute: "2-digit"
4197
+ }).format(new Date(value));
4198
+ } catch {
4199
+ return null;
4200
+ }
4201
+ }
4202
+ function ChannelListHeading({ className = "", id: id6, title, connectionLabel }) {
4203
+ const helpId = React8.useId();
4204
+ return h2(
4205
+ "div",
4206
+ { className: `${className} dim-listHeading`.trim() },
4207
+ h2(
4208
+ "div",
4209
+ { className: "dim-listTitle" },
4210
+ h2("h3", id6 ? { id: id6 } : null, title),
4211
+ h2(
4212
+ "span",
4213
+ { className: "dim-channelHelp" },
4214
+ h2("button", {
4215
+ type: "button",
4216
+ className: "dim-channelHelpButton",
4217
+ "aria-label": "\u67E5\u770B\u6D88\u606F\u901A\u9053\u8BF4\u660E",
4218
+ "aria-describedby": helpId
4219
+ }, h2("span", { "aria-hidden": "true" }, "?")),
4220
+ h2(
4221
+ "span",
4222
+ {
4223
+ id: helpId,
4224
+ className: "dim-channelTooltip",
4225
+ role: "tooltip"
4226
+ },
4227
+ h2("span", null, "\u6D88\u606F\u901A\u9053"),
4228
+ h2("strong", null, connectionLabel)
4229
+ )
4230
+ )
4231
+ )
4232
+ );
4233
+ }
4234
+ function BotStatusMeta({
4235
+ className = "",
4236
+ dotClassName = "",
4237
+ tone,
4238
+ stateLabel: stateLabel2,
4239
+ lastCheckedAt,
4240
+ formatCheckedTime: formatCheckedTime2,
4241
+ healthState
4242
+ }) {
4243
+ return h2(
4244
+ "div",
4245
+ { className: "dim-botHealthGroup" },
4246
+ h2(
4247
+ "div",
4248
+ {
4249
+ className: `${className} dim-botHealth`.trim(),
4250
+ ...healthState ? { "data-health": healthState } : {}
4251
+ },
4252
+ h2("span", {
4253
+ className: `${dotClassName} dim-healthDot`.trim(),
4254
+ "data-tone": tone
4255
+ }),
4256
+ h2("span", null, stateLabel2)
4257
+ ),
4258
+ h2(
4259
+ "div",
4260
+ { className: "dim-lastChecked" },
4261
+ h2("span", null, "\u6700\u8FD1\u68C0\u67E5"),
4262
+ h2("span", null, formatCheckedTime2(lastCheckedAt))
4263
+ )
4264
+ );
4265
+ }
4266
+ function LastMessageErrorSummary({ className = "", error }) {
4267
+ if (!error) return null;
4268
+ const occurredAt = messageErrorTime(error.at);
4269
+ return h2(
4270
+ "div",
4271
+ {
4272
+ className: `${className} dim-cardSummary`.trim(),
4273
+ role: "status"
4274
+ },
4275
+ h2("strong", null, "\u6700\u8FD1\u4E00\u6761\u6D88\u606F\u5904\u7406\u5931\u8D25"),
4276
+ "\uFF1A",
4277
+ h2("span", null, error.message),
4278
+ error.details ? h2(ConnectionError, { error, showMessage: false }) : null,
4279
+ "\uFF08",
4280
+ h2("span", null, "\u9519\u8BEF\u7801"),
4281
+ ` ${error.code} \xB7 `,
4282
+ h2("span", null, "\u53C2\u8003\u53F7"),
4283
+ ` ${error.referenceId}`,
4284
+ occurredAt ? h2(
4285
+ React8.Fragment,
4286
+ null,
4287
+ " \xB7 ",
4288
+ h2("time", { dateTime: new Date(error.at).toISOString() }, occurredAt)
4289
+ ) : null,
4290
+ "\uFF09"
4291
+ );
4292
+ }
4293
+
4294
+ // plugin-src/client/channels/shared/collapsible-account.js
4295
+ var AccountSectionContext = React9.createContext(null);
4296
+ function AccountSettingsToggle() {
4297
+ const { open, toggle, contentId } = React9.useContext(AccountSectionContext);
4298
+ return h2(
4299
+ "button",
4300
+ {
4301
+ type: "button",
4302
+ className: "dim-accountSettingsToggle",
4303
+ "aria-label": open ? "\u6536\u8D77\u8BE5\u8D26\u53F7\u7684\u8BBE\u7F6E" : "\u5C55\u5F00\u8BE5\u8D26\u53F7\u7684\u8BBE\u7F6E",
4304
+ "aria-expanded": open ? "true" : "false",
4305
+ "aria-controls": contentId,
4306
+ onClick: (event) => {
4307
+ event.stopPropagation();
4308
+ toggle();
4309
+ }
4310
+ },
4311
+ h2(SettingsGlyph),
4312
+ h2("svg", {
4313
+ className: "dim-collapsibleChevron",
4314
+ viewBox: "0 0 12 16",
4315
+ width: 12,
4316
+ height: 16,
4317
+ fill: "none",
4318
+ stroke: "currentColor",
4319
+ strokeWidth: 1.8,
4320
+ strokeLinecap: "round",
4321
+ strokeLinejoin: "round",
4322
+ "aria-hidden": "true"
4323
+ }, h2("path", { d: "M2 6 6 10 10 6" }))
4324
+ );
4325
+ }
4121
4326
  function CollapsibleAccountSection({
4122
4327
  header,
4328
+ settings,
4123
4329
  defaultOpen = false,
4124
4330
  open: controlledOpen,
4125
4331
  onToggle,
@@ -4127,57 +4333,59 @@ function CollapsibleAccountSection({
4127
4333
  className = "",
4128
4334
  children
4129
4335
  }) {
4130
- const [uncontrolledOpen, setUncontrolledOpen] = React8.useState(defaultOpen);
4336
+ const [uncontrolledOpen, setUncontrolledOpen] = React9.useState(defaultOpen);
4337
+ const generatedId = React9.useId();
4131
4338
  const open = controlledOpen ?? uncontrolledOpen;
4132
- const contentId = id6 ? `${id6}-content` : void 0;
4339
+ const contentId = `${id6 ?? generatedId}-content`;
4133
4340
  const toggle = () => {
4134
4341
  if (controlledOpen === void 0) setUncontrolledOpen((value) => !value);
4135
4342
  onToggle?.(!open);
4136
4343
  };
4137
- const onKeyDown = (event) => {
4138
- if (event.key === "Enter" || event.key === " " || event.key === "Spacebar") {
4139
- event.preventDefault();
4140
- toggle();
4141
- }
4142
- };
4143
4344
  return h2(
4144
- "div",
4145
- {
4146
- className: `dim-collapsibleAccount ${open ? "is-open" : ""} ${className}`.trim(),
4147
- "data-open": open ? "true" : "false"
4148
- },
4345
+ AccountSectionContext.Provider,
4346
+ { value: { open, toggle, contentId } },
4149
4347
  h2(
4150
4348
  "div",
4151
4349
  {
4152
- className: "dim-collapsibleHead",
4153
- role: "button",
4154
- tabIndex: 0,
4155
- onClick: toggle,
4156
- onKeyDown,
4157
- "aria-expanded": open ? "true" : "false",
4158
- "aria-controls": contentId,
4159
- "aria-label": open ? "\u6536\u8D77\u8BE5\u8D26\u53F7\u7684\u8BBE\u7F6E" : "\u5C55\u5F00\u8BE5\u8D26\u53F7\u7684\u8BBE\u7F6E"
4350
+ className: `dim-collapsibleAccount ${open ? "is-open" : ""} ${className}`.trim(),
4351
+ "data-open": open ? "true" : "false"
4160
4352
  },
4161
- h2("div", { className: "dim-collapsibleHeaderContent" }, header),
4162
- h2("span", { className: "dim-collapsibleChevron", "aria-hidden": "true" })
4163
- ),
4164
- h2(
4165
- "div",
4166
- {
4167
- id: contentId,
4168
- className: "dim-collapsibleBody",
4169
- role: "region"
4170
- },
4171
- h2("div", { className: "dim-collapsibleBodyInner" }, children)
4353
+ h2(
4354
+ "div",
4355
+ {
4356
+ className: "dim-collapsibleHead",
4357
+ onClick: toggle
4358
+ },
4359
+ h2("div", { className: "dim-collapsibleHeaderContent" }, header)
4360
+ ),
4361
+ h2(
4362
+ "div",
4363
+ {
4364
+ id: contentId,
4365
+ className: "dim-collapsibleBody",
4366
+ role: "region"
4367
+ },
4368
+ h2(
4369
+ "div",
4370
+ { className: "dim-collapsibleBodyInner" },
4371
+ settings ? h2(
4372
+ "div",
4373
+ { className: "dim-accountSettingsHeader" },
4374
+ h2("span", null, "\u5E38\u7528\u914D\u7F6E"),
4375
+ settings
4376
+ ) : null,
4377
+ children
4378
+ )
4379
+ )
4172
4380
  )
4173
4381
  );
4174
4382
  }
4175
4383
 
4176
4384
  // plugin-src/client/workspace-editor.js
4177
- var React10 = __toESM(require("react"), 1);
4385
+ var React11 = __toESM(require("react"), 1);
4178
4386
 
4179
4387
  // plugin-src/client/workspace-directory-picker.js
4180
- var React9 = __toESM(require("react"), 1);
4388
+ var React10 = __toESM(require("react"), 1);
4181
4389
  var import_react_dom2 = require("react-dom");
4182
4390
  function pickerErrorCode(error) {
4183
4391
  return error?.rpcError?.code ?? error?.code;
@@ -4198,7 +4406,7 @@ function pickerErrorMessage(error) {
4198
4406
  return error?.rpcError?.message ?? error?.message ?? "\u65E0\u6CD5\u8BFB\u53D6\u76EE\u5F55\uFF0C\u8BF7\u91CD\u8BD5\u3002";
4199
4407
  }
4200
4408
  function FolderIcon() {
4201
- return React9.createElement(
4409
+ return React10.createElement(
4202
4410
  "svg",
4203
4411
  {
4204
4412
  viewBox: "0 0 24 24",
@@ -4209,11 +4417,11 @@ function FolderIcon() {
4209
4417
  strokeLinejoin: "round",
4210
4418
  "aria-hidden": "true"
4211
4419
  },
4212
- React9.createElement("path", { d: "M3.5 7.25A2.25 2.25 0 0 1 5.75 5h4.1l1.8 2h6.6a2.25 2.25 0 0 1 2.25 2.25v7A2.75 2.75 0 0 1 17.75 19h-12A2.25 2.25 0 0 1 3.5 16.75v-9.5Z" })
4420
+ React10.createElement("path", { d: "M3.5 7.25A2.25 2.25 0 0 1 5.75 5h4.1l1.8 2h6.6a2.25 2.25 0 0 1 2.25 2.25v7A2.75 2.75 0 0 1 17.75 19h-12A2.25 2.25 0 0 1 3.5 16.75v-9.5Z" })
4213
4421
  );
4214
4422
  }
4215
4423
  function ChevronIcon() {
4216
- return React9.createElement("svg", {
4424
+ return React10.createElement("svg", {
4217
4425
  viewBox: "0 0 20 20",
4218
4426
  fill: "none",
4219
4427
  stroke: "currentColor",
@@ -4221,7 +4429,7 @@ function ChevronIcon() {
4221
4429
  strokeLinecap: "round",
4222
4430
  strokeLinejoin: "round",
4223
4431
  "aria-hidden": "true"
4224
- }, React9.createElement("path", { d: "m7.5 4.5 5 5.5-5 5.5" }));
4432
+ }, React10.createElement("path", { d: "m7.5 4.5 5 5.5-5 5.5" }));
4225
4433
  }
4226
4434
  function displayCrumbs(listing) {
4227
4435
  const homeIndex = listing.crumbs.findIndex((crumb) => crumb.path === listing.home);
@@ -4237,28 +4445,28 @@ function WorkspaceDirectoryPicker({
4237
4445
  onPicked,
4238
4446
  onCancel
4239
4447
  }) {
4240
- const [listing, setListing] = React9.useState(null);
4241
- const [loading, setLoading] = React9.useState(false);
4242
- const [error, setError] = React9.useState(null);
4243
- const [pathDraft, setPathDraft] = React9.useState(startPath ?? "");
4244
- const [showHidden, setShowHidden] = React9.useState(false);
4245
- const [retryKey, setRetryKey] = React9.useState(0);
4246
- const requestRef = React9.useRef(0);
4247
- const controllerRef = React9.useRef(null);
4248
- const dialogRef = React9.useRef(null);
4249
- const bodyRef = React9.useRef(null);
4250
- const titleId = React9.useId();
4251
- const noticeId = React9.useId();
4252
- const pathInputId = React9.useId();
4253
- const errorId = React9.useId();
4254
- const initialPathRef = React9.useRef(startPath);
4255
- const onPickedRef = React9.useRef(onPicked);
4256
- const onCancelRef = React9.useRef(onCancel);
4257
- const busyRef = React9.useRef(busy);
4448
+ const [listing, setListing] = React10.useState(null);
4449
+ const [loading, setLoading] = React10.useState(false);
4450
+ const [error, setError] = React10.useState(null);
4451
+ const [pathDraft, setPathDraft] = React10.useState(startPath ?? "");
4452
+ const [showHidden, setShowHidden] = React10.useState(false);
4453
+ const [retryKey, setRetryKey] = React10.useState(0);
4454
+ const requestRef = React10.useRef(0);
4455
+ const controllerRef = React10.useRef(null);
4456
+ const dialogRef = React10.useRef(null);
4457
+ const bodyRef = React10.useRef(null);
4458
+ const titleId = React10.useId();
4459
+ const noticeId = React10.useId();
4460
+ const pathInputId = React10.useId();
4461
+ const errorId = React10.useId();
4462
+ const initialPathRef = React10.useRef(startPath);
4463
+ const onPickedRef = React10.useRef(onPicked);
4464
+ const onCancelRef = React10.useRef(onCancel);
4465
+ const busyRef = React10.useRef(busy);
4258
4466
  onPickedRef.current = onPicked;
4259
4467
  onCancelRef.current = onCancel;
4260
4468
  busyRef.current = busy;
4261
- const loadDirectory = React9.useCallback(async (path, { reportError = true } = {}) => {
4469
+ const loadDirectory = React10.useCallback(async (path, { reportError = true } = {}) => {
4262
4470
  const request = requestRef.current + 1;
4263
4471
  requestRef.current = request;
4264
4472
  controllerRef.current?.abort();
@@ -4282,7 +4490,7 @@ function WorkspaceDirectoryPicker({
4282
4490
  if (request === requestRef.current) setLoading(false);
4283
4491
  }
4284
4492
  }, [picker]);
4285
- React9.useEffect(() => {
4493
+ React10.useEffect(() => {
4286
4494
  if (!open) return void 0;
4287
4495
  let active = true;
4288
4496
  setListing(null);
@@ -4362,10 +4570,10 @@ function WorkspaceDirectoryPicker({
4362
4570
  "nav",
4363
4571
  { className: "dim-directoryCrumbs", "aria-label": "\u5F53\u524D\u76EE\u5F55" },
4364
4572
  crumbs.map((crumb, index) => h2(
4365
- React9.Fragment,
4573
+ React10.Fragment,
4366
4574
  { key: crumb.path },
4367
4575
  index > 0 ? h2("span", { className: "dim-directoryCrumbSeparator", "aria-hidden": "true" }, "\u203A") : null,
4368
- React9.createElement("button", {
4576
+ React10.createElement("button", {
4369
4577
  type: "button",
4370
4578
  title: crumb.path,
4371
4579
  disabled: loading || busy,
@@ -4428,7 +4636,7 @@ function WorkspaceDirectoryPicker({
4428
4636
  ) : listing ? entries.length > 0 ? h2("ul", { className: "dim-directoryList" }, entries.map((entry) => h2(
4429
4637
  "li",
4430
4638
  { key: entry.path },
4431
- React9.createElement(
4639
+ React10.createElement(
4432
4640
  "button",
4433
4641
  {
4434
4642
  type: "button",
@@ -4437,7 +4645,7 @@ function WorkspaceDirectoryPicker({
4437
4645
  onClick: () => void loadDirectory(entry.path)
4438
4646
  },
4439
4647
  h2("span", { className: "dim-directoryFolder" }, h2(FolderIcon)),
4440
- React9.createElement("span", { className: "dim-directoryName" }, entry.name),
4648
+ React10.createElement("span", { className: "dim-directoryName" }, entry.name),
4441
4649
  h2("span", { className: "dim-directoryChevron" }, h2(ChevronIcon))
4442
4650
  )
4443
4651
  ))) : h2(
@@ -4490,21 +4698,21 @@ function WorkspaceDirectoryPicker({
4490
4698
  }
4491
4699
 
4492
4700
  // plugin-src/client/workspace-editor.js
4493
- var WorkspaceDirectoryPickerContext = React10.createContext(null);
4701
+ var WorkspaceDirectoryPickerContext = React11.createContext(null);
4494
4702
  function WorkspaceEditor({ workspace, directoryPicker, disabled = false, onSave }) {
4495
- const sharedDirectoryPicker = React10.useContext(WorkspaceDirectoryPickerContext);
4703
+ const sharedDirectoryPicker = React11.useContext(WorkspaceDirectoryPickerContext);
4496
4704
  const activeDirectoryPicker = directoryPicker ?? sharedDirectoryPicker;
4497
- const [open, setOpen] = React10.useState(false);
4498
- const [saving, setSaving] = React10.useState(false);
4499
- const [error, setError] = React10.useState(null);
4500
- const editButtonRef = React10.useRef(null);
4501
- const savingRef = React10.useRef(false);
4502
- const close = React10.useCallback(() => {
4705
+ const [open, setOpen] = React11.useState(false);
4706
+ const [saving, setSaving] = React11.useState(false);
4707
+ const [error, setError] = React11.useState(null);
4708
+ const editButtonRef = React11.useRef(null);
4709
+ const savingRef = React11.useRef(false);
4710
+ const close = React11.useCallback(() => {
4503
4711
  setOpen(false);
4504
4712
  setError(null);
4505
4713
  queueMicrotask(() => editButtonRef.current?.focus?.());
4506
4714
  }, []);
4507
- const pick = React10.useCallback(async (value) => {
4715
+ const pick = React11.useCallback(async (value) => {
4508
4716
  if (!value || savingRef.current || disabled) return;
4509
4717
  if (value === workspace) {
4510
4718
  close();
@@ -4541,7 +4749,7 @@ function WorkspaceEditor({ workspace, directoryPicker, disabled = false, onSave
4541
4749
  disabled: disabled || !activeDirectoryPicker
4542
4750
  }, "\u9009\u62E9\u76EE\u5F55")
4543
4751
  ),
4544
- workspace ? React10.createElement("code", {
4752
+ workspace ? React11.createElement("code", {
4545
4753
  className: "dim-workspacePath",
4546
4754
  title: workspace
4547
4755
  }, workspace) : h2("code", { className: "dim-workspacePath" }, "\u672A\u8BBE\u7F6E"),
@@ -4558,7 +4766,7 @@ function WorkspaceEditor({ workspace, directoryPicker, disabled = false, onSave
4558
4766
  }
4559
4767
 
4560
4768
  // plugin-src/client/context-enhancement.js
4561
- var React11 = __toESM(require("react"), 1);
4769
+ var React12 = __toESM(require("react"), 1);
4562
4770
  var import_react_dom3 = require("react-dom");
4563
4771
  var FIELD_LABELS = Object.freeze({
4564
4772
  channel: "\u6E20\u9053",
@@ -4803,7 +5011,7 @@ function ContextEnhancementScopeEditor({
4803
5011
  );
4804
5012
  }
4805
5013
  function ContextEnhancementDialog({ config, groupSupported, disabled, onSave, onClose, returnFocusRef, id: id6 }) {
4806
- const [draft, setDraft] = React11.useState(() => {
5014
+ const [draft, setDraft] = React12.useState(() => {
4807
5015
  const normalized = normalizeContextEnhancementConfig(config);
4808
5016
  return {
4809
5017
  ...normalized,
@@ -4812,23 +5020,23 @@ function ContextEnhancementDialog({ config, groupSupported, disabled, onSave, on
4812
5020
  } : {}
4813
5021
  };
4814
5022
  });
4815
- const [saving, setSaving] = React11.useState(false);
4816
- const [error, setError] = React11.useState(null);
4817
- const [activeScope, setActiveScope] = React11.useState("direct");
4818
- const savingRef = React11.useRef(false);
4819
- const dialogRef = React11.useRef(null);
4820
- const mountedRef = React11.useRef(true);
4821
- const groupTabRef = React11.useRef(null);
4822
- const directTabRef = React11.useRef(null);
4823
- const titleId = React11.useId();
4824
- const descriptionId = React11.useId();
4825
- const scopeIdPrefix = React11.useId();
5023
+ const [saving, setSaving] = React12.useState(false);
5024
+ const [error, setError] = React12.useState(null);
5025
+ const [activeScope, setActiveScope] = React12.useState("direct");
5026
+ const savingRef = React12.useRef(false);
5027
+ const dialogRef = React12.useRef(null);
5028
+ const mountedRef = React12.useRef(true);
5029
+ const groupTabRef = React12.useRef(null);
5030
+ const directTabRef = React12.useRef(null);
5031
+ const titleId = React12.useId();
5032
+ const descriptionId = React12.useId();
5033
+ const scopeIdPrefix = React12.useId();
4826
5034
  const groupGuidanceExample = localizeText(CONTEXT_GROUP_GUIDANCE_EXAMPLE);
4827
5035
  const directGuidanceExample = localizeText(CONTEXT_DIRECT_GUIDANCE_EXAMPLE);
4828
5036
  const busy = disabled || saving;
4829
5037
  const scopeKinds = ["direct", "group"];
4830
5038
  const tabRefs = { group: groupTabRef, direct: directTabRef };
4831
- React11.useEffect(() => {
5039
+ React12.useEffect(() => {
4832
5040
  mountedRef.current = true;
4833
5041
  dialogRef.current?.focus?.();
4834
5042
  const keepFocus = (event) => {
@@ -5019,17 +5227,17 @@ function ContextEnhancementDialog({ config, groupSupported, disabled, onSave, on
5019
5227
  return globalThis.document?.body ? (0, import_react_dom3.createPortal)(content, document.body) : content;
5020
5228
  }
5021
5229
  function ContextEnhancementEditor({ config, groupSupported = true, disabled = false, onSave }) {
5022
- const [open, setOpen] = React11.useState(false);
5023
- const entryRef = React11.useRef(null);
5024
- const dialogId = React11.useId();
5025
- const statusId = React11.useId();
5230
+ const [open, setOpen] = React12.useState(false);
5231
+ const entryRef = React12.useRef(null);
5232
+ const dialogId = React12.useId();
5233
+ const statusId = React12.useId();
5026
5234
  const saved = normalizeContextEnhancementConfig(config);
5027
5235
  const label = contextEnhancementLabel(groupSupported ? saved : {
5028
5236
  ...saved,
5029
5237
  group: { ...saved.group, enabled: false }
5030
5238
  });
5031
5239
  return h2(
5032
- React11.Fragment,
5240
+ React12.Fragment,
5033
5241
  null,
5034
5242
  h2(
5035
5243
  "button",
@@ -5063,10 +5271,10 @@ function ContextEnhancementEditor({ config, groupSupported = true, disabled = fa
5063
5271
  }
5064
5272
 
5065
5273
  // plugin-src/client/workspace-snapshot-fence.js
5066
- var React12 = __toESM(require("react"), 1);
5274
+ var React13 = __toESM(require("react"), 1);
5067
5275
  function useWorkspaceSnapshotFence() {
5068
- const state = React12.useRef({ version: 0, pendingMutations: 0 });
5069
- return React12.useMemo(() => Object.freeze({
5276
+ const state = React13.useRef({ version: 0, pendingMutations: 0 });
5277
+ return React13.useMemo(() => Object.freeze({
5070
5278
  beginStatus() {
5071
5279
  return state.current.pendingMutations === 0 ? state.current.version : null;
5072
5280
  },
@@ -5088,170 +5296,6 @@ function useWorkspaceSnapshotFence() {
5088
5296
  }), []);
5089
5297
  }
5090
5298
 
5091
- // plugin-src/client/channel-card-meta.js
5092
- var React13 = __toESM(require("react"), 1);
5093
- var BotSettingsContext = React13.createContext(Object.freeze({
5094
- openBotSettings() {
5095
- }
5096
- }));
5097
- function SettingsGlyph() {
5098
- return h2(
5099
- "svg",
5100
- {
5101
- viewBox: "0 0 24 24",
5102
- width: 16,
5103
- height: 16,
5104
- fill: "none",
5105
- stroke: "currentColor",
5106
- strokeWidth: 1.8,
5107
- strokeLinecap: "round",
5108
- strokeLinejoin: "round",
5109
- "aria-hidden": "true"
5110
- },
5111
- h2("circle", { cx: 12, cy: 12, r: 3 }),
5112
- h2("path", { d: "M19.4 15a1.7 1.7 0 0 0 .34 1.88l.06.06-2.83 2.83-.06-.06a1.7 1.7 0 0 0-1.88-.34 1.7 1.7 0 0 0-1.03 1.55V21h-4v-.08A1.7 1.7 0 0 0 8.97 19.4a1.7 1.7 0 0 0-1.88.34l-.06.06-2.83-2.83.06-.06A1.7 1.7 0 0 0 4.6 15a1.7 1.7 0 0 0-1.52-1.03H3v-4h.08A1.7 1.7 0 0 0 4.6 8.97a1.7 1.7 0 0 0-.34-1.88l-.06-.06L7.03 4.2l.06.06a1.7 1.7 0 0 0 1.88.34A1.7 1.7 0 0 0 10 3.08V3h4v.08a1.7 1.7 0 0 0 1.03 1.52 1.7 1.7 0 0 0 1.88-.34l.06-.06 2.83 2.83-.06.06a1.7 1.7 0 0 0-.34 1.88A1.7 1.7 0 0 0 20.92 10H21v4h-.08A1.7 1.7 0 0 0 19.4 15Z" })
5113
- );
5114
- }
5115
- function BotSettingsButton({
5116
- channel: channel6,
5117
- botId,
5118
- botName,
5119
- connected,
5120
- accessPolicy,
5121
- channelSettings
5122
- }) {
5123
- const { openBotSettings } = React13.useContext(BotSettingsContext);
5124
- const tooltipId = React13.useId();
5125
- return h2(
5126
- "span",
5127
- { className: "dim-botSettingsAction" },
5128
- h2("button", {
5129
- type: "button",
5130
- className: "dim-botSettingsButton",
5131
- "data-delivery-channel": channel6,
5132
- "aria-label": "\u66F4\u591A\u673A\u5668\u4EBA\u8BBE\u7F6E",
5133
- "aria-describedby": tooltipId,
5134
- onClick: () => openBotSettings?.({
5135
- ...channelSettings && typeof channelSettings === "object" ? channelSettings : {},
5136
- channel: channel6,
5137
- botId,
5138
- botName,
5139
- connected: Boolean(connected),
5140
- accessPolicy
5141
- })
5142
- }, h2(SettingsGlyph)),
5143
- h2("span", {
5144
- id: tooltipId,
5145
- className: "dim-botSettingsTooltip",
5146
- role: "tooltip"
5147
- }, "\u66F4\u591A\u673A\u5668\u4EBA\u8BBE\u7F6E")
5148
- );
5149
- }
5150
- function messageErrorTime(value) {
5151
- try {
5152
- return new Intl.DateTimeFormat(isEnglish() ? "en-US" : "zh-CN", {
5153
- year: "numeric",
5154
- month: "2-digit",
5155
- day: "2-digit",
5156
- hour: "2-digit",
5157
- minute: "2-digit"
5158
- }).format(new Date(value));
5159
- } catch {
5160
- return null;
5161
- }
5162
- }
5163
- function ChannelListHeading({ className = "", id: id6, title, connectionLabel }) {
5164
- const helpId = React13.useId();
5165
- return h2(
5166
- "div",
5167
- { className: `${className} dim-listHeading`.trim() },
5168
- h2(
5169
- "div",
5170
- { className: "dim-listTitle" },
5171
- h2("h3", id6 ? { id: id6 } : null, title),
5172
- h2(
5173
- "span",
5174
- { className: "dim-channelHelp" },
5175
- h2("button", {
5176
- type: "button",
5177
- className: "dim-channelHelpButton",
5178
- "aria-label": "\u67E5\u770B\u6D88\u606F\u901A\u9053\u8BF4\u660E",
5179
- "aria-describedby": helpId
5180
- }, h2("span", { "aria-hidden": "true" }, "?")),
5181
- h2(
5182
- "span",
5183
- {
5184
- id: helpId,
5185
- className: "dim-channelTooltip",
5186
- role: "tooltip"
5187
- },
5188
- h2("span", null, "\u6D88\u606F\u901A\u9053"),
5189
- h2("strong", null, connectionLabel)
5190
- )
5191
- )
5192
- )
5193
- );
5194
- }
5195
- function BotStatusMeta({
5196
- className = "",
5197
- dotClassName = "",
5198
- tone,
5199
- stateLabel: stateLabel2,
5200
- lastCheckedAt,
5201
- formatCheckedTime: formatCheckedTime2,
5202
- healthState
5203
- }) {
5204
- return h2(
5205
- "div",
5206
- { className: "dim-botHealthGroup" },
5207
- h2(
5208
- "div",
5209
- {
5210
- className: `${className} dim-botHealth`.trim(),
5211
- ...healthState ? { "data-health": healthState } : {}
5212
- },
5213
- h2("span", {
5214
- className: `${dotClassName} dim-healthDot`.trim(),
5215
- "data-tone": tone
5216
- }),
5217
- h2("span", null, stateLabel2)
5218
- ),
5219
- h2(
5220
- "div",
5221
- { className: "dim-lastChecked" },
5222
- h2("span", null, "\u6700\u8FD1\u68C0\u67E5"),
5223
- h2("span", null, formatCheckedTime2(lastCheckedAt))
5224
- )
5225
- );
5226
- }
5227
- function LastMessageErrorSummary({ className = "", error }) {
5228
- if (!error) return null;
5229
- const occurredAt = messageErrorTime(error.at);
5230
- return h2(
5231
- "div",
5232
- {
5233
- className: `${className} dim-cardSummary`.trim(),
5234
- role: "status"
5235
- },
5236
- h2("strong", null, "\u6700\u8FD1\u4E00\u6761\u6D88\u606F\u5904\u7406\u5931\u8D25"),
5237
- "\uFF1A",
5238
- h2("span", null, error.message),
5239
- error.details ? h2(ConnectionError, { error, showMessage: false }) : null,
5240
- "\uFF08",
5241
- h2("span", null, "\u9519\u8BEF\u7801"),
5242
- ` ${error.code} \xB7 `,
5243
- h2("span", null, "\u53C2\u8003\u53F7"),
5244
- ` ${error.referenceId}`,
5245
- occurredAt ? h2(
5246
- React13.Fragment,
5247
- null,
5248
- " \xB7 ",
5249
- h2("time", { dateTime: new Date(error.at).toISOString() }, occurredAt)
5250
- ) : null,
5251
- "\uFF09"
5252
- );
5253
- }
5254
-
5255
5299
  // plugin-src/client/channels/dingtalk/styles.js
5256
5300
  var DINGTALK_STYLE_ID = "xmanrui-dsh-im-dingtalk-settings";
5257
5301
  var CSS = String.raw`
@@ -5686,6 +5730,13 @@ function AccountCard({
5686
5730
  h2(
5687
5731
  CollapsibleAccountSection,
5688
5732
  {
5733
+ settings: h2(BotSettingsButton, {
5734
+ channel: "dingtalk",
5735
+ botId: account.botId,
5736
+ botName: account.bot.name,
5737
+ connected: account.connected,
5738
+ accessPolicy: account.accessPolicy
5739
+ }),
5689
5740
  id: `ddt-settings-${account.botId.replace(/[^a-zA-Z0-9_-]/g, "-")}`,
5690
5741
  header: h2(
5691
5742
  "div",
@@ -5721,13 +5772,7 @@ function AccountCard({
5721
5772
  lastCheckedAt: account.health.lastCheckedAt,
5722
5773
  formatCheckedTime: checkedTime
5723
5774
  }),
5724
- h2(BotSettingsButton, {
5725
- channel: "dingtalk",
5726
- botId: account.botId,
5727
- botName: account.bot.name,
5728
- connected: account.connected,
5729
- accessPolicy: account.accessPolicy
5730
- })
5775
+ h2(AccountSettingsToggle)
5731
5776
  )
5732
5777
  )
5733
5778
  },
@@ -6586,6 +6631,13 @@ function createTokenChannelSettings(definition) {
6586
6631
  h2(
6587
6632
  CollapsibleAccountSection,
6588
6633
  {
6634
+ settings: h2(BotSettingsButton, {
6635
+ channel: channel6.toLowerCase(),
6636
+ botId: account.botId,
6637
+ botName: account.bot.name,
6638
+ connected: account.connected,
6639
+ accessPolicy: account.accessPolicy
6640
+ }),
6589
6641
  id: `tok-settings-${account.botId.replace(/[^a-zA-Z0-9_-]/g, "-")}`,
6590
6642
  header: h2(
6591
6643
  "div",
@@ -6625,13 +6677,7 @@ function createTokenChannelSettings(definition) {
6625
6677
  lastCheckedAt: account.health.lastCheckedAt,
6626
6678
  formatCheckedTime: checkedTime2
6627
6679
  }),
6628
- h2(BotSettingsButton, {
6629
- channel: channel6.toLowerCase(),
6630
- botId: account.botId,
6631
- botName: account.bot.name,
6632
- connected: account.connected,
6633
- accessPolicy: account.accessPolicy
6634
- })
6680
+ h2(AccountSettingsToggle)
6635
6681
  )
6636
6682
  )
6637
6683
  },
@@ -7999,6 +8045,18 @@ function BotCard({
7999
8045
  h2(
8000
8046
  CollapsibleAccountSection,
8001
8047
  {
8048
+ settings: h2(BotSettingsButton, {
8049
+ channel: "feishu",
8050
+ botId: connection.botId,
8051
+ botName: bot.name,
8052
+ connected,
8053
+ accessPolicy: connection.accessPolicy,
8054
+ channelSettings: {
8055
+ groupResponseMode: connection.groupResponseMode,
8056
+ groupTopicReply: connection.groupTopicReply,
8057
+ groupMessagePermissionGranted: connection.groupMessagePermissionGranted
8058
+ }
8059
+ }),
8002
8060
  id: `bxf-settings-${connection.botId.replace(/[^a-zA-Z0-9_-]/g, "-")}`,
8003
8061
  header: h2(
8004
8062
  "div",
@@ -8039,18 +8097,7 @@ function BotCard({
8039
8097
  formatCheckedTime,
8040
8098
  healthState: stateForDisplay
8041
8099
  }),
8042
- h2(BotSettingsButton, {
8043
- channel: "feishu",
8044
- botId: connection.botId,
8045
- botName: bot.name,
8046
- connected,
8047
- accessPolicy: connection.accessPolicy,
8048
- channelSettings: {
8049
- groupResponseMode: connection.groupResponseMode,
8050
- groupTopicReply: connection.groupTopicReply,
8051
- groupMessagePermissionGranted: connection.groupMessagePermissionGranted
8052
- }
8053
- })
8100
+ h2(AccountSettingsToggle)
8054
8101
  )
8055
8102
  )
8056
8103
  },
@@ -9935,6 +9982,13 @@ function AccountCard2({
9935
9982
  h2(
9936
9983
  CollapsibleAccountSection,
9937
9984
  {
9985
+ settings: h2(BotSettingsButton, {
9986
+ channel: "qq",
9987
+ botId: account.botId,
9988
+ botName: account.bot.name,
9989
+ connected: account.connected,
9990
+ accessPolicy: account.accessPolicy
9991
+ }),
9938
9992
  id: `qq-settings-${account.botId.replace(/[^a-zA-Z0-9_-]/g, "-")}`,
9939
9993
  header: h2(
9940
9994
  "div",
@@ -9970,13 +10024,7 @@ function AccountCard2({
9970
10024
  lastCheckedAt: account.health.lastCheckedAt,
9971
10025
  formatCheckedTime: checkedTime3
9972
10026
  }),
9973
- h2(BotSettingsButton, {
9974
- channel: "qq",
9975
- botId: account.botId,
9976
- botName: account.bot.name,
9977
- connected: account.connected,
9978
- accessPolicy: account.accessPolicy
9979
- })
10027
+ h2(AccountSettingsToggle)
9980
10028
  )
9981
10029
  )
9982
10030
  },
@@ -11440,6 +11488,13 @@ function AccountCard3({
11440
11488
  h2(
11441
11489
  CollapsibleAccountSection,
11442
11490
  {
11491
+ settings: h2(BotSettingsButton, {
11492
+ channel: "wecom",
11493
+ botId: account.botId,
11494
+ botName: account.bot.name,
11495
+ connected: account.connected,
11496
+ accessPolicy: account.accessPolicy
11497
+ }),
11443
11498
  id: `wec-settings-${account.botId.replace(/[^a-zA-Z0-9_-]/g, "-")}`,
11444
11499
  header: h2(
11445
11500
  "div",
@@ -11475,13 +11530,7 @@ function AccountCard3({
11475
11530
  lastCheckedAt: account.health.lastCheckedAt,
11476
11531
  formatCheckedTime: checkedTime4
11477
11532
  }),
11478
- h2(BotSettingsButton, {
11479
- channel: "wecom",
11480
- botId: account.botId,
11481
- botName: account.bot.name,
11482
- connected: account.connected,
11483
- accessPolicy: account.accessPolicy
11484
- })
11533
+ h2(AccountSettingsToggle)
11485
11534
  )
11486
11535
  )
11487
11536
  },
@@ -12368,6 +12417,13 @@ function AccountCard4({
12368
12417
  h2(
12369
12418
  CollapsibleAccountSection,
12370
12419
  {
12420
+ settings: h2(BotSettingsButton, {
12421
+ channel: "wecomApp",
12422
+ botId: account.botId,
12423
+ botName: account.bot.name,
12424
+ connected: account.connected,
12425
+ accessPolicy: account.accessPolicy
12426
+ }),
12371
12427
  id: elementId,
12372
12428
  header: h2(
12373
12429
  "div",
@@ -12402,13 +12458,7 @@ function AccountCard4({
12402
12458
  lastCheckedAt: account.health.lastCheckedAt,
12403
12459
  formatCheckedTime: checkedTime5
12404
12460
  }),
12405
- h2(BotSettingsButton, {
12406
- channel: "wecomApp",
12407
- botId: account.botId,
12408
- botName: account.bot.name,
12409
- connected: account.connected,
12410
- accessPolicy: account.accessPolicy
12411
- })
12461
+ h2(AccountSettingsToggle)
12412
12462
  )
12413
12463
  )
12414
12464
  },
@@ -13219,6 +13269,13 @@ function AccountCard5({
13219
13269
  h2(
13220
13270
  CollapsibleAccountSection,
13221
13271
  {
13272
+ settings: h2(BotSettingsButton, {
13273
+ channel: "weixin",
13274
+ botId: account.botId,
13275
+ botName: account.bot.name,
13276
+ connected: account.connected,
13277
+ accessPolicy: account.accessPolicy
13278
+ }),
13222
13279
  id: `dxw-settings-${account.botId.replace(/[^a-zA-Z0-9_-]/g, "-")}`,
13223
13280
  header: h2(
13224
13281
  "div",
@@ -13249,13 +13306,7 @@ function AccountCard5({
13249
13306
  lastCheckedAt: account.health.lastCheckedAt,
13250
13307
  formatCheckedTime: checkedTime6
13251
13308
  }),
13252
- h2(BotSettingsButton, {
13253
- channel: "weixin",
13254
- botId: account.botId,
13255
- botName: account.bot.name,
13256
- connected: account.connected,
13257
- accessPolicy: account.accessPolicy
13258
- })
13309
+ h2(AccountSettingsToggle)
13259
13310
  )
13260
13311
  )
13261
13312
  },
@@ -14353,6 +14404,13 @@ function WhatsappAccountCard({
14353
14404
  h2(
14354
14405
  CollapsibleAccountSection,
14355
14406
  {
14407
+ settings: h2(BotSettingsButton, {
14408
+ channel: "whatsapp",
14409
+ botId: account.botId,
14410
+ botName: account.bot.name,
14411
+ connected: account.connected,
14412
+ accessPolicy: account.accessPolicy
14413
+ }),
14356
14414
  id: `wsp-settings-${account.botId.replace(/[^a-zA-Z0-9_-]/g, "-")}`,
14357
14415
  header: h2(
14358
14416
  "div",
@@ -14391,13 +14449,7 @@ function WhatsappAccountCard({
14391
14449
  lastCheckedAt: account.health.lastCheckedAt,
14392
14450
  formatCheckedTime: checkedTime7
14393
14451
  }),
14394
- h2(BotSettingsButton, {
14395
- channel: "whatsapp",
14396
- botId: account.botId,
14397
- botName: account.bot.name,
14398
- connected: account.connected,
14399
- accessPolicy: account.accessPolicy
14400
- })
14452
+ h2(AccountSettingsToggle)
14401
14453
  )
14402
14454
  )
14403
14455
  },
@@ -18655,10 +18707,15 @@ var CSS14 = String.raw`
18655
18707
  .dim-panel .dim-botCardBody { position: relative; min-width: 0; width: 100%; max-width: 100%; padding: 12px 8px; }
18656
18708
  .dim-collapsibleAccount { min-width: 0; display: flex; flex-direction: column; }
18657
18709
  .dim-collapsibleHead { min-width: 0; display: flex; align-items: center; gap: 4px; cursor: pointer; user-select: none; -webkit-user-select: none; }
18658
- .dim-collapsibleHead:focus-visible { outline: 2px solid var(--dsw-alias-state-business-primary, #3370ff); outline-offset: 2px; border-radius: 8px; }
18659
18710
  .dim-collapsibleHeaderContent { min-width: 0; flex: 1 1 auto; display: flex; align-items: center; }
18660
- .dim-collapsibleChevron { flex: 0 0 auto; display: inline-flex; align-items: center; justify-content: center; width: 9px; height: 9px; border-right: 1.6px solid var(--dsw-alias-label-tertiary, #8f959e); border-bottom: 1.6px solid var(--dsw-alias-label-tertiary, #8f959e); transform: rotate(-45deg); transition: transform .22s cubic-bezier(.4, 0, .2, 1); transform-origin: 50% 50%; }
18661
- .dim-collapsibleAccount.is-open .dim-collapsibleChevron { transform: rotate(45deg); }
18711
+ /* Keep the original header footprint; center both icons with equal side space. */
18712
+ .dim-accountSettingsToggle { flex: none; width: 45px; height: 32px; display: inline-flex; gap: 5px; align-items: center; justify-content: center; padding: 0; border: 0; border-radius: 8px; color: var(--dsw-alias-state-business-primary, #3370ff); background: color-mix(in srgb, var(--dsw-alias-state-business-primary, #3370ff) 8%, var(--dsw-alias-bg-layer-1, #fff)); cursor: pointer; }
18713
+ .dim-accountSettingsToggle > svg { flex: none; display: block; }
18714
+ .dim-accountSettingsToggle:hover { background: color-mix(in srgb, var(--dsw-alias-state-business-primary, #3370ff) 14%, var(--dsw-alias-bg-layer-1, #fff)); }
18715
+ .dim-accountSettingsToggle:focus-visible { outline: 2px solid var(--dsw-alias-state-business-primary, #3370ff); outline-offset: 2px; }
18716
+ .dim-collapsibleChevron { width: 12px; height: 16px; transition: transform .22s cubic-bezier(.4, 0, .2, 1); transform-origin: 50% 50%; }
18717
+ .dim-accountSettingsToggle[aria-expanded="true"] .dim-collapsibleChevron { transform: rotate(180deg); }
18718
+ .dim-accountSettingsHeader { display: flex; align-items: center; justify-content: space-between; gap: 12px; margin-top: 12px; padding-top: 8px; border-top: 1px solid var(--dsw-alias-border-l2, #e5e6eb); color: var(--dsw-alias-label-secondary, #646a73); font-size: 12px; }
18662
18719
  /* Animate height without measuring content; hide collapsed controls from focus and accessibility. */
18663
18720
  .dim-collapsibleBody { display: grid; grid-template-rows: 0fr; transition: grid-template-rows .22s cubic-bezier(.4, 0, .2, 1); }
18664
18721
  .dim-collapsibleAccount.is-open > .dim-collapsibleBody { grid-template-rows: 1fr; }
@@ -18683,11 +18740,10 @@ var CSS14 = String.raw`
18683
18740
  .dim-panel .dim-botCard .dim-healthDot[data-tone="warning"] { background: var(--dsw-alias-state-warn-primary, #d97706); }
18684
18741
  .dim-panel .dim-botCard .dim-healthDot[data-tone="error"] { background: var(--dsw-alias-state-error-primary, #d54941); }
18685
18742
  .dim-botSettingsAction { position: relative; flex: none; display: inline-flex; }
18686
- .dim-botSettingsButton { width: 32px; height: 32px; display: grid; place-items: center; padding: 0; border: 0; border-radius: 8px; color: var(--dsw-alias-label-secondary, #646a73); background: transparent; cursor: pointer; transition: color .15s ease, background .15s ease; }
18743
+ .dim-botSettingsButton { min-height: 32px; display: inline-flex; align-items: center; gap: 6px; padding: 0 6px; border: 0; border-radius: 8px; color: var(--dsw-alias-state-business-primary, #3370ff); background: transparent; font: inherit; font-size: 12px; white-space: nowrap; cursor: pointer; transition: color .15s ease, background .15s ease; }
18687
18744
  .dim-botSettingsButton:hover { color: var(--dsw-alias-label-primary, #1f2329); background: var(--dsw-alias-interactive-bg-hover, #eef0f3); }
18688
18745
  .dim-botSettingsButton:focus-visible { outline: 2px solid var(--dsw-alias-state-business-primary, #3370ff); outline-offset: 2px; }
18689
- .dim-botSettingsTooltip { position: absolute; top: calc(100% + 6px); right: 0; z-index: 30; width: max-content; padding: 6px 9px; border: 1px solid var(--dsw-alias-border-l2, #dfe1e5); border-radius: 7px; color: var(--dsw-alias-label-primary, #1f2329); background: var(--dsw-alias-bg-layer-3, #fff); box-shadow: 0 8px 24px rgb(31 35 41 / 14%); font-size: 11px; line-height: 16px; opacity: 0; visibility: hidden; transform: translateY(-3px); pointer-events: none; transition: opacity .15s ease, transform .15s ease, visibility .15s ease; }
18690
- .dim-botSettingsAction:hover .dim-botSettingsTooltip, .dim-botSettingsAction:focus-within .dim-botSettingsTooltip { opacity: 1; visibility: visible; transform: translateY(0); }
18746
+ .dim-moreSettingsChevron { width: 6px; height: 6px; margin-right: 2px; border-right: 1.5px solid currentColor; border-bottom: 1.5px solid currentColor; transform: rotate(-45deg); }
18691
18747
  .dim-deliveryPage { min-width: 0; display: grid; }
18692
18748
  .dim-deliveryHeader { min-width: 0; display: flex; align-items: center; justify-content: space-between; gap: 16px; }
18693
18749
  .dim-botSettingsTabsBar { min-width: 0; margin-top: 10px; border-bottom: 1px solid var(--dsw-alias-border-l2, #dfe1e5); }
@@ -19271,14 +19327,17 @@ function summary(snapshot, action, error) {
19271
19327
  if (snapshot?.job?.state === "restart-required" || snapshot?.blockedReason === "pending-restart") {
19272
19328
  return "\u5DF2\u5B89\u88C5\uFF0C\u5F85\u624B\u52A8\u91CD\u542F";
19273
19329
  }
19274
- if (snapshot?.job?.state === "completed") return "\u66F4\u65B0\u5DF2\u751F\u6548";
19275
- if (snapshot?.job?.state === "failed") return "\u66F4\u65B0\u5931\u8D25";
19276
- if (snapshot?.job?.state === "interrupted") return "\u4E0A\u6B21\u66F4\u65B0\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u68C0\u67E5\u5B89\u88C5\u72B6\u6001\u540E\u91CD\u8BD5\u3002";
19277
19330
  if (error) return "\u66F4\u65B0\u8BF7\u6C42\u5931\u8D25";
19331
+ if (!snapshot?.job?.recoverable) {
19332
+ if (snapshot?.job?.state === "failed") return "\u66F4\u65B0\u5931\u8D25";
19333
+ if (snapshot?.job?.state === "interrupted") return "\u4E0A\u6B21\u66F4\u65B0\u5DF2\u4E2D\u65AD\uFF0C\u8BF7\u68C0\u67E5\u5B89\u88C5\u72B6\u6001\u540E\u91CD\u8BD5\u3002";
19334
+ }
19335
+ if (snapshot?.blockedReason === "no-update") return "\u5F53\u524D\u7248\u672C\u65E0\u9700\u66F4\u65B0";
19336
+ if (snapshot?.blockedReason) return "\u6682\u65F6\u65E0\u6CD5\u5B89\u88C5\u66F4\u65B0";
19278
19337
  if (snapshot?.canInstall) return "\u53D1\u73B0\u65B0\u7248\u672C";
19279
19338
  if (snapshot?.checkedAt && snapshot.latestVersion === snapshot.runningVersion) return "\u5DF2\u662F\u6700\u65B0\u7248\u672C";
19280
- if (snapshot?.blockedReason === "no-update") return "\u5F53\u524D\u7248\u672C\u65E0\u9700\u66F4\u65B0";
19281
19339
  if (snapshot?.checkedAt) return "\u5DF2\u83B7\u53D6 npm \u6700\u65B0\u7248\u672C";
19340
+ if (snapshot?.job?.state === "completed") return "\u66F4\u65B0\u5DF2\u751F\u6548";
19282
19341
  return "\u68C0\u67E5 npm \u6700\u65B0\u7248\u672C\uFF0C\u4E0D\u4F1A\u81EA\u52A8\u5B89\u88C5\u3002";
19283
19342
  }
19284
19343
  function retainDialogFocus(event) {
@@ -19293,7 +19352,7 @@ function manualUpdateCommand(snapshot) {
19293
19352
  const targets = [
19294
19353
  snapshot.latestVersion,
19295
19354
  pendingRestart ? snapshot.installedVersion : null,
19296
- snapshot.job?.state !== "completed" ? snapshot.job?.targetVersion : null
19355
+ snapshot.job?.state !== "completed" && !snapshot.job?.recoverable ? snapshot.job?.targetVersion : null
19297
19356
  ].filter(validVersion);
19298
19357
  const version = targets.length ? [...targets, snapshot.runningVersion, snapshot.installedVersion].filter(validVersion).sort(import_rcompare.default)[0] : "latest";
19299
19358
  return `dsh plugin --profile ${profileArgument} add -w @xmanrui/dsh-im@${version}`;
@@ -19601,9 +19660,11 @@ function UpdatePanel({ rpcCall, clientVersion, onStatus }) {
19601
19660
  const blocked = BLOCKED_REASONS[snapshot?.blockedReason] ?? ERROR_MESSAGES[snapshot?.blockedReason];
19602
19661
  const canConfirm = snapshot?.canInstall && snapshot.checkId && !activeJob && !restartRequired;
19603
19662
  const versionsDiffer = snapshot && clientVersion && snapshot.runningVersion !== clientVersion;
19604
- const failedJob = ["failed", "interrupted"].includes(snapshot?.job?.state);
19663
+ const failedJob = ["failed", "interrupted"].includes(snapshot?.job?.state) && !snapshot.job.recoverable;
19605
19664
  const jobMessage = snapshot?.job?.message;
19606
- const targetVersion = snapshot?.job?.targetVersion;
19665
+ const targetVersion = activeJob || restartRequired ? snapshot?.job?.targetVersion : null;
19666
+ const historicalTargetVersion = !activeJob && !restartRequired ? snapshot?.job?.targetVersion : null;
19667
+ const latestVersion = !activeJob && !restartRequired && !error && snapshot?.checkedAt ? snapshot.latestVersion : null;
19607
19668
  const manualCommand = manualUpdateCommand(snapshot);
19608
19669
  const buttonLabel = action === "checking" ? "\u68C0\u67E5\u4E2D\u2026" : action === "starting" || activeJob ? "\u6B63\u5728\u66F4\u65B0\u2026" : restartRequired ? "\u5F85\u624B\u52A8\u91CD\u542F" : snapshot?.canInstall ? "\u66F4\u65B0\u81F3" : "\u68C0\u67E5\u66F4\u65B0";
19609
19670
  return h2(
@@ -19617,7 +19678,7 @@ function UpdatePanel({ rpcCall, clientVersion, onStatus }) {
19617
19678
  onClick: () => {
19618
19679
  setOpen(true);
19619
19680
  if (restartRequired) void refreshStatus();
19620
- else if (!snapshot?.canInstall && !snapshot?.job) void check();
19681
+ else if (!snapshot?.canInstall && !activeJob && !uncertainInstall) void check();
19621
19682
  }
19622
19683
  }, buttonLabel, buttonLabel === "\u66F4\u65B0\u81F3" ? ` v${snapshot.latestVersion}` : null),
19623
19684
  open ? h2(
@@ -19643,6 +19704,18 @@ function UpdatePanel({ rpcCall, clientVersion, onStatus }) {
19643
19704
  h2("dt", null, "\u76EE\u6807\u7248\u672C"),
19644
19705
  h2("dd", null, `v${targetVersion}`)
19645
19706
  ) : null,
19707
+ latestVersion ? h2(
19708
+ React31.Fragment,
19709
+ null,
19710
+ h2("dt", null, "\u6700\u65B0\u7248\u672C"),
19711
+ h2("dd", null, `v${latestVersion}`)
19712
+ ) : null,
19713
+ historicalTargetVersion ? h2(
19714
+ React31.Fragment,
19715
+ null,
19716
+ h2("dt", null, "\u4E0A\u6B21\u66F4\u65B0\u76EE\u6807"),
19717
+ h2("dd", null, `v${historicalTargetVersion}`)
19718
+ ) : null,
19646
19719
  h2("dt", null, "\u76EE\u6807 profile"),
19647
19720
  h2("dd", null, snapshot?.profileName ?? "\u65E0\u6CD5\u786E\u8BA4")
19648
19721
  ),