dsh-plugin-litellm-bridge 2.0.3 → 2.0.4
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.
|
@@ -279,7 +279,7 @@ window.__ModuleLoader__.load({
|
|
|
279
279
|
},
|
|
280
280
|
}),
|
|
281
281
|
h('span', { style: { fontWeight: 600 } }, 'LiteLLM 网关'),
|
|
282
|
-
h('span', { style: S.badge(tone === 'ok' ? T.success : tone === 'error' ? T.error : T.warn) }, label),
|
|
282
|
+
h('span', { style: S.badge(tone === 'ok' ? T.success : tone === 'error' ? T.error : T.warn) }, safeText(label)),
|
|
283
283
|
st?.owned && h('span', { style: S.badge(T.brand, tint(T.brand, 14)) }, '本插件托管'),
|
|
284
284
|
!st?.owned && st?.alive && h('span', { style: S.badge() }, '外部运行 · 不接管'),
|
|
285
285
|
h('span', { style: { marginLeft: 'auto', display: 'flex', gap: 6 } },
|
|
@@ -290,11 +290,18 @@ window.__ModuleLoader__.load({
|
|
|
290
290
|
),
|
|
291
291
|
),
|
|
292
292
|
h('div', { style: { padding: '0 12px 10px', ...S.mono, fontSize: 11, color: T.labelSecondary, lineHeight: 1.7 } },
|
|
293
|
-
|
|
294
|
-
|
|
295
|
-
|
|
293
|
+
// 【必须 safeText】这些值来自宿主 RPC,可能是对象 / undefined / Error。
|
|
294
|
+
// 直接插进子节点会触发 React #62(Objects are not valid as a React child),
|
|
295
|
+
// 整个设置页白屏 —— 实测「点测试连通性后白屏」就是这个原因之一。
|
|
296
|
+
h('div', null, `地址:${safeText(st?.url, '—')}`),
|
|
297
|
+
h('div', null,
|
|
298
|
+
`托管策略:${safeText(st?.ownership, '—')}` +
|
|
299
|
+
(st?.autoStart === false ? '(autoStartGateway 已关闭)' : '')),
|
|
300
|
+
st?.lastError && h('div', { style: { color: T.error } },
|
|
301
|
+
`最近错误:${safeText(st.lastError)}`),
|
|
296
302
|
!st?.lastError && st?.lastExit?.abnormal &&
|
|
297
|
-
h('div', { style: { color: T.error } },
|
|
303
|
+
h('div', { style: { color: T.error } },
|
|
304
|
+
`异常退出记录:code=${safeText(st.lastExit.code, '?')}`),
|
|
298
305
|
),
|
|
299
306
|
);
|
|
300
307
|
}
|
|
@@ -338,7 +345,7 @@ window.__ModuleLoader__.load({
|
|
|
338
345
|
h('select', {
|
|
339
346
|
style: { ...S.inputAuto, minWidth: 110 },
|
|
340
347
|
value: pid, onChange: (e) => setPid(e.target.value),
|
|
341
|
-
}, ...(profileIds || []).map((p) => h('option', { key: p, value: p }, p))),
|
|
348
|
+
}, ...(profileIds || []).map((p) => h('option', { key: p, value: p }, safeText(p)))),
|
|
342
349
|
h('select', {
|
|
343
350
|
style: { ...S.inputAuto, minWidth: 110 },
|
|
344
351
|
value: agentType, onChange: (e) => setAgentType(e.target.value),
|
|
@@ -373,7 +380,7 @@ window.__ModuleLoader__.load({
|
|
|
373
380
|
},
|
|
374
381
|
h('span', { style: S.badge() }, String(i + 1)),
|
|
375
382
|
i === 0 && h('span', { style: S.badge(T.brand, tint(T.brand, 14)) }, '首选'),
|
|
376
|
-
h('span', { style: { ...S.mono, flex: 1, wordBreak: 'break-all' } }, m),
|
|
383
|
+
h('span', { style: { ...S.mono, flex: 1, wordBreak: 'break-all' } }, safeText(m)),
|
|
377
384
|
row && h('span', { style: { ...S.mono, fontSize: 11, color: row.ok ? T.success : T.error } },
|
|
378
385
|
row.ok ? '✓' : '✗'),
|
|
379
386
|
row && row.latencyMs != null && h('span', {
|
|
@@ -386,7 +393,7 @@ window.__ModuleLoader__.load({
|
|
|
386
393
|
}),
|
|
387
394
|
),
|
|
388
395
|
|
|
389
|
-
err && h('div', { style: S.notice('error') }, err),
|
|
396
|
+
err && h('div', { style: S.notice('error') }, safeText(err)),
|
|
390
397
|
|
|
391
398
|
result && h('div', null,
|
|
392
399
|
h('div', { style: { ...S.row, marginBottom: 8 } },
|
|
@@ -740,7 +747,7 @@ window.__ModuleLoader__.load({
|
|
|
740
747
|
|
|
741
748
|
return h('div', { key: at },
|
|
742
749
|
h('div', { style: S.h2Row },
|
|
743
|
-
h('h2', { style: S.h2 }, groupLabel),
|
|
750
|
+
h('h2', { style: S.h2 }, safeText(groupLabel)),
|
|
744
751
|
isSub && h('span', { style: S.badge() }, '仅子 Agent 使用'),
|
|
745
752
|
h('span', { style: { ...S.mono, fontSize: 11, color: T.labelSecondary } },
|
|
746
753
|
chainLen ? `链长 ${chainLen}` : '未配置'),
|
|
@@ -931,11 +938,11 @@ window.__ModuleLoader__.load({
|
|
|
931
938
|
h('div', { style: { ...S.row, marginBottom: 10 } },
|
|
932
939
|
h('select', { style: { ...S.input, width: 'auto' }, value: fAgent, onChange: (e) => setFAgent(e.target.value) },
|
|
933
940
|
h('option', { value: '' }, '全部 agent-type'),
|
|
934
|
-
agents.map((a) => h('option', { key: a, value: a }, a)),
|
|
941
|
+
agents.map((a) => h('option', { key: a, value: a }, safeText(a))),
|
|
935
942
|
),
|
|
936
943
|
h('select', { style: { ...S.input, width: 'auto' }, value: fProfile, onChange: (e) => setFProfile(e.target.value) },
|
|
937
944
|
h('option', { value: '' }, '全部 profile'),
|
|
938
|
-
profiles.map((p) => h('option', { key: p, value: p }, p)),
|
|
945
|
+
profiles.map((p) => h('option', { key: p, value: p }, safeText(p))),
|
|
939
946
|
),
|
|
940
947
|
h('span', { style: { marginLeft: 'auto', ...S.mono, fontSize: 11, color: T.labelSecondary } },
|
|
941
948
|
`显示 ${shown.length} / 最多 ${limit} 条`),
|
|
@@ -964,9 +971,9 @@ window.__ModuleLoader__.load({
|
|
|
964
971
|
l.time ? String(l.time).replace('T', ' ').slice(0, 19) : '—'),
|
|
965
972
|
isGwEvent
|
|
966
973
|
? h('span', { style: S.badge(T.brand, tint(T.brand, 14)) }, 'gateway')
|
|
967
|
-
: h('span', { style: S.badge() }, l.agentType),
|
|
968
|
-
!isGwEvent && h('span', { style: S.badge() }, l.profile),
|
|
969
|
-
h('span', { style: { ...S.mono, fontWeight: 600 } }, l.model),
|
|
974
|
+
: h('span', { style: S.badge() }, safeText(l.agentType, '-')),
|
|
975
|
+
!isGwEvent && h('span', { style: S.badge() }, safeText(l.profile, '-')),
|
|
976
|
+
h('span', { style: { ...S.mono, fontWeight: 600 } }, safeText(l.model)),
|
|
970
977
|
l.source === 'local' && !isGwEvent && h('span', { style: S.badge(T.brand, tint(T.brand, 14)) }, 'local'),
|
|
971
978
|
k === 'fallback' && h('span', { style: S.badge(T.warn, tint(T.warn, 14)) }, 'FALLBACK'),
|
|
972
979
|
k === 'failed' && h('span', { style: S.badge(T.error, tint(T.error, 14)) }, '失败'),
|
|
@@ -1054,7 +1061,7 @@ window.__ModuleLoader__.load({
|
|
|
1054
1061
|
style: S.input, value: profile, onChange: (e) => setProfile(e.target.value),
|
|
1055
1062
|
},
|
|
1056
1063
|
h('option', { value: '' }, '(不绑定)'),
|
|
1057
|
-
profileIds.map((p) => h('option', { key: p, value: p }, p)),
|
|
1064
|
+
profileIds.map((p) => h('option', { key: p, value: p }, safeText(p))),
|
|
1058
1065
|
),
|
|
1059
1066
|
h('div', { style: S.hint },
|
|
1060
1067
|
'绑定后:本会话的 root 请求按该 profile 的 root 链走;spawn 的子 Agent 按同 profile 的 coder/research 链走。'),
|
package/package.json
CHANGED
|
@@ -1,6 +1,6 @@
|
|
|
1
1
|
{
|
|
2
2
|
"name": "dsh-plugin-litellm-bridge",
|
|
3
|
-
"version": "2.0.
|
|
3
|
+
"version": "2.0.4",
|
|
4
4
|
"description": "LiteLLM gateway bridge for DSH: assemble root / coder / research fallback chains from the DSH model pool and hand the order to a LiteLLM gateway that executes retries and fallbacks. The plugin performs no routing itself.",
|
|
5
5
|
"keywords": [
|
|
6
6
|
"dsh",
|