@spzxg/cli-ui 0.6.9 → 0.6.10

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/dist/cli-ui.js CHANGED
@@ -1,4 +1,4 @@
1
- import { C as a, b as i, d as r, e as t, f as o, h as C, i as l, j as n, k as m, m as d, l as u, n as w, o as B, p as f } from "./cli-ui-embed-CtZDwP8y.js";
1
+ import { C as a, b as i, d as r, e as t, f as o, h as C, i as l, j as n, k as m, m as d, l as u, n as w, o as B, p as f } from "./cli-ui-embed-CbxWozLO.js";
2
2
  export {
3
3
  a as CliBoard,
4
4
  i as CliBrowserView,
package/package.json CHANGED
@@ -1,6 +1,6 @@
1
1
  {
2
2
  "name": "@spzxg/cli-ui",
3
- "version": "0.6.9",
3
+ "version": "0.6.10",
4
4
  "type": "module",
5
5
  "description": "相互联动的 CliMsgList、CliChat、CliBoard,支持任务中枢和完整 Operator 工作区。",
6
6
  "main": "src/index.ts",
@@ -234,9 +234,11 @@ function ChatInner({ slots, passiveContext = true, configurationBusy, onClear, j
234
234
  const agent = task?.agent ?? conv?.turns[conv.turns.length - 1]?.agent ?? null;
235
235
  const draftScope = store.draftScope ? `${store.draftScope}:${key ?? `new:${instanceId}`}` : key ?? `new:${instanceId}`;
236
236
  const initialOptions = newConversation ?? store.getNewConversationOptions();
237
+ const executionReady = !batch && (!key || !!job);
238
+ const executionEnabled = showComposer && executionReady && (cfg.composer.agentSelector || cfg.composer.executionMode);
237
239
  const execution = useExecutionConfig({ client: store.client, scope: draftScope,
238
240
  target: key && !isNew ? key : null, running: running || batchPending,
239
- enabled: showComposer && (cfg.composer.agentSelector || cfg.composer.executionMode),
241
+ enabled: executionEnabled, ready: executionReady,
240
242
  initial: { ...(initialOptions?.agent ? { agent: initialOptions.agent } : {}), ...initialOptions?.executionConfig },
241
243
  });
242
244
  const agentText = labelOf(execution.config?.agent ?? agent);
@@ -852,8 +854,8 @@ function ChatInner({ slots, passiveContext = true, configurationBusy, onClear, j
852
854
  model: execution.config?.model, reasoning: execution.config?.reasoning, permission_mode: execution.config?.permission_mode }}
853
855
  agents={execution.config?.agents} caps={executionAgent?.capabilities} defaults={executionAgent?.defaults}
854
856
  showAgent={cfg.composer.agentSelector} showPermission={cfg.composer.executionMode}
855
- unavailableReason={executionReadOnly ? "当前接入仅支持读取执行设置。" : execution.error ?? (execution.loading ? "正在读取执行设置…" : undefined)}
856
- disabled={composerDisabled || running || batchPending || !!configurationBusy || execution.loading || executionReadOnly}
857
+ unavailableReason={batch ? "一次性任务沿用任务执行设置,不支持在对话中修改。" : executionReadOnly ? "当前接入仅支持读取执行设置。" : execution.error ?? (!executionEnabled || execution.loading ? "正在读取执行设置…" : undefined)}
858
+ disabled={!executionEnabled || composerDisabled || running || batchPending || !!configurationBusy || execution.loading || executionReadOnly}
857
859
  onSetAgent={agent => execution.save({ agent, model: null, reasoning: null, permission_mode: null })}
858
860
  onSetModel={model => execution.save({ model })} onSetReasoning={reasoning => execution.save({ reasoning })}
859
861
  onSetPermission={permission_mode => execution.save({ permission_mode })} />
@@ -211,7 +211,7 @@ export function Composer({ draft, placeholder, disabled, disabledHint, running,
211
211
  {options.fileUpload && !disabled && <>
212
212
  <input ref={fileRef} type="file" accept={uploadDocument ? FILE_UPLOAD_ACCEPT : ACCEPT_ATTR} multiple hidden onChange={(e) => { addFiles(Array.from(e.target.files ?? [])); e.target.value = ""; }} />
213
213
  <button type="button" className="cli-attach" disabled={sending} aria-label={uploadDocument ? "添加文件" : "添加文档"} title={uploadDocument ? "添加文件(也可拖拽进来);HTML、Markdown 最大 100 MiB,其他支持类型最大 10 MiB" : `添加文档:${ACCEPTED_LABEL}(也可拖拽进来)`}
214
- onClick={() => fileRef.current?.click()}>{Icon.plus()} <span>{options.fileButtonText}</span></button>
214
+ onClick={() => fileRef.current?.click()}>{Icon.plus()}{options.fileButtonText && <span>{options.fileButtonText}</span>}</button>
215
215
  </>}
216
216
  {toolbar}
217
217
  {options.hints && !disabled && <span className="hint comp-hint-extra">Shift + Enter 换行</span>}
@@ -18,9 +18,9 @@ function validate(result: ExecutionConfiguration) {
18
18
  }
19
19
 
20
20
  /** 按对话隔离读取与保存,不轮询;换对话后的迟到响应不覆盖当前选择。 */
21
- export function useExecutionConfig({ client, scope, target, enabled, initial, running }: {
21
+ export function useExecutionConfig({ client, scope, target, enabled, ready = true, initial, running }: {
22
22
  client: ConversationBackend; scope: string; target: string | null; enabled: boolean;
23
- initial?: ExecutionOptions; running: boolean;
23
+ initial?: ExecutionOptions; running: boolean; ready?: boolean;
24
24
  }) {
25
25
  const [view, setView] = useState<{ scope: string; config?: ExecutionConfiguration; error?: string; loading: boolean; saveFailed?: boolean }>({ scope, loading: false });
26
26
  const current = useRef(scope);
@@ -34,7 +34,7 @@ export function useExecutionConfig({ client, scope, target, enabled, initial, ru
34
34
  const reload = useCallback(async () => {
35
35
  const serial = ++request.current;
36
36
  const active = () => mounted.current && current.current === scope && request.current === serial;
37
- if (!enabled && !readComposerDraft(scope).executionUncertain) return;
37
+ if (!ready || (!enabled && !readComposerDraft(scope).executionUncertain)) return;
38
38
  if (!client.getExecutionConfig) {
39
39
  setView({ scope, loading: false, error: "当前接入尚未提供执行设置。" });
40
40
  return;
@@ -50,7 +50,7 @@ export function useExecutionConfig({ client, scope, target, enabled, initial, ru
50
50
  } catch (error) {
51
51
  if (active()) setView(value => ({ ...(value.scope === scope ? value : {}), scope, error: errorText(error), loading: false }));
52
52
  }
53
- }, [client, scope, target, enabled]);
53
+ }, [client, scope, target, enabled, ready]);
54
54
  useEffect(() => { void reload(); return () => { request.current++; }; }, [reload]);
55
55
  const wasRunning = useRef(running);
56
56
  useEffect(() => {
@@ -1420,7 +1420,7 @@ button.pop-item:hover{background:var(--surface-2);}
1420
1420
  .composer .comp-box{border-radius:26px;border-color:var(--line);box-shadow:0 4px 20px rgba(0,0,0,.035);}
1421
1421
  .composer .comp-box:focus-within{border-color:var(--line-strong);box-shadow:0 6px 24px rgba(0,0,0,.055);}
1422
1422
  .composer .comp-toolbar{gap:6px;padding:6px 12px 12px;}
1423
- .composer .comp-area{padding:18px 20px 12px;}
1423
+ .composer .comp-area{padding:12px 20px 4px;}
1424
1424
  .composer .attach-chip.image{width:108px;height:88px;border-radius:12px;}
1425
1425
  .composer .attach-chip.image>img{height:100%;object-fit:cover;}
1426
1426
  .composer .attach-chip .attach-x{width:26px;height:26px;top:4px;right:4px;font-size:16px;}
@@ -1429,7 +1429,7 @@ button.pop-item:hover{background:var(--surface-2);}
1429
1429
  .composer .attach-row .attach-chip{flex:none;}
1430
1430
  .composer .cli-blocks{max-height:min(30vh,180px);}
1431
1431
  @container(max-width:420px){
1432
- .composer .comp-area{padding:14px 16px 8px;}
1432
+ .composer .comp-area{padding:12px 16px 4px;}
1433
1433
  .composer .comp-toolbar{gap:4px;padding:6px 10px 10px;}
1434
1434
  .composer .comp-setting{padding:6px 9px;}
1435
1435
  .composer .attach-chip.image{width:86px;height:76px;}
package/src/operator.css CHANGED
@@ -1420,7 +1420,7 @@
1420
1420
  .cli-ui .composer .comp-box{border-radius:26px;border-color:var(--line);box-shadow:0 4px 20px rgba(0,0,0,.035);}
1421
1421
  .cli-ui .composer .comp-box:focus-within{border-color:var(--line-strong);box-shadow:0 6px 24px rgba(0,0,0,.055);}
1422
1422
  .cli-ui .composer .comp-toolbar{gap:6px;padding:6px 12px 12px;}
1423
- .cli-ui .composer .comp-area{padding:18px 20px 12px;}
1423
+ .cli-ui .composer .comp-area{padding:12px 20px 4px;}
1424
1424
  .cli-ui .composer .attach-chip.image{width:108px;height:88px;border-radius:12px;}
1425
1425
  .cli-ui .composer .attach-chip.image>img{height:100%;object-fit:cover;}
1426
1426
  .cli-ui .composer .attach-chip .attach-x{width:26px;height:26px;top:4px;right:4px;font-size:16px;}
@@ -1429,7 +1429,7 @@
1429
1429
  .cli-ui .composer .attach-row .attach-chip{flex:none;}
1430
1430
  .cli-ui .composer .cli-blocks{max-height:min(30vh,180px);}
1431
1431
  @container(max-width:420px){
1432
- .cli-ui .composer .comp-area{padding:14px 16px 8px;}
1432
+ .cli-ui .composer .comp-area{padding:12px 16px 4px;}
1433
1433
  .cli-ui .composer .comp-toolbar{gap:4px;padding:6px 10px 10px;}
1434
1434
  .cli-ui .composer .comp-setting{padding:6px 9px;}
1435
1435
  .cli-ui .composer .attach-chip.image{width:86px;height:76px;}
package/src/styles.css CHANGED
@@ -53,8 +53,9 @@
53
53
  .cli-ui .sess-head .crumb{overflow-wrap:anywhere;}
54
54
  .cli-ui .cli-export{white-space:nowrap;}
55
55
  .cli-ui .comp-area textarea{min-width:0;}
56
- .cli-ui .comp-foot{gap:8px;padding:8px 10px;background:transparent;border-top:0;flex-wrap:wrap;}
56
+ .cli-ui .composer .comp-foot{gap:4px;padding:4px 10px;background:transparent;border-top:0;flex-wrap:wrap;}
57
57
  .cli-ui .comp-foot>.comp-control{flex:0 0 auto;}
58
+ .cli-ui .comp-foot .permission{padding-inline:6px;}
58
59
  .cli-ui .cli-attach{display:inline-flex;justify-content:center;align-items:center;gap:5px;min-width:44px;min-height:44px;padding:0 8px;border-radius:7px;color:var(--ink-3);font-size:12px;}
59
60
  @media(hover:hover) and (pointer:fine){.cli-ui .cli-attach:hover{background:var(--surface-2);color:var(--ink);}}
60
61
  .cli-ui .cli-attach svg{width:22px;height:22px;}