mirror of
https://github.com/openclaw/openclaw.git
synced 2026-05-06 06:50:43 +00:00
fix: compact progress draft lines
This commit is contained in:
@@ -11,6 +11,7 @@ Docs: https://docs.openclaw.ai
|
||||
### Changes
|
||||
|
||||
- Channels/streaming: add unified `streaming.mode: "progress"` drafts with auto single-word status labels and shared progress configuration across Discord, Telegram, Matrix, Slack, and Microsoft Teams.
|
||||
- Channels/streaming: cap progress-draft tool lines by default so edited progress boxes avoid jumpy reflow from long wrapped lines.
|
||||
- Agents/verbose: use compact explain-mode tool summaries for `/verbose` and progress drafts by default, with `agents.defaults.toolProgressDetail: "raw"` and per-agent overrides for debugging raw command/detail output.
|
||||
- Agents/commands: add `/steer <message>` for queue-independent steering of the active current-session run without starting a new turn when the session is idle. (#76934)
|
||||
- Tools/BTW: add `/side` as a text and native slash-command alias for `/btw` side questions.
|
||||
|
||||
@@ -1,4 +1,4 @@
|
||||
3e7cbffbe3849b5201716f359dde9089d61d618c1a4206255c20887a855d85a9 config-baseline.json
|
||||
ac95b4ab62408454636ce559e6d023df3c29b8b936b3aa4dde37779d29a5a099 config-baseline.json
|
||||
31ec333df9f8b92c7656ac7107cecd5860dd02e08f7e18c7c674dc47a8811baa config-baseline.core.json
|
||||
655d1309b70505e73198df20c5088784290b33098efd42027d3c09beeb3704a7 config-baseline.channel.json
|
||||
055fae0d0067a751dc10125af7421da45633f73519c94c982d02b0c4eb2bdf67 config-baseline.plugin.json
|
||||
9458dc89aa13dd07d83f69d943535099a96e8278eb7ac8ae5cf2f713631592f7 config-baseline.plugin.json
|
||||
|
||||
@@ -1,2 +1,2 @@
|
||||
0dd4f5abaf72f0d6b3fe5777cbf16c7a8c8052eece17436dc0ac2809b0ea27de plugin-sdk-api-baseline.json
|
||||
2c2170cf2f1193f7dbecdef3ccd1b601992407e3d99863d1aa13cb1817c238fd plugin-sdk-api-baseline.jsonl
|
||||
701356478634a8f3e71f941ed21a00e0456d947d287edcafb56231013b27a057 plugin-sdk-api-baseline.json
|
||||
ed17426dd5e9db4b83db77162e7490eee3c0439170c1a9d1e84c01d7027d580c plugin-sdk-api-baseline.jsonl
|
||||
|
||||
@@ -217,6 +217,12 @@ Limit how many lines stay visible:
|
||||
}
|
||||
```
|
||||
|
||||
Progress lines are compacted automatically to reduce chat-bubble reflow while the draft is edited.
|
||||
|
||||
OpenClaw truncates long progress lines by default so repeated draft edits do not
|
||||
wrap differently on every update. The prefix stays readable, and long details
|
||||
such as paths or raw commands are shortened with an ellipsis.
|
||||
|
||||
Keep the single progress draft but hide tool and task lines:
|
||||
|
||||
```json5
|
||||
|
||||
@@ -186,6 +186,16 @@ describe("channel-streaming", () => {
|
||||
).toBe("Shelling\n🛠️ Exec\n• plain update");
|
||||
});
|
||||
|
||||
it("bounds progress draft line length to reduce edit reflow", () => {
|
||||
expect(
|
||||
formatChannelProgressDraftText({
|
||||
entry: { streaming: { progress: { label: "Shelling" } } },
|
||||
lines: ["x".repeat(80)],
|
||||
formatLine: (line) => `\`${line}\``,
|
||||
}),
|
||||
).toBe(`Shelling\n• \`${"x".repeat(71)}…\``);
|
||||
});
|
||||
|
||||
it("formats progress draft lines with shared tool display labels", () => {
|
||||
expect(
|
||||
formatChannelProgressDraftLine({
|
||||
|
||||
@@ -110,6 +110,7 @@ export const DEFAULT_PROGRESS_DRAFT_LABELS = [
|
||||
] as const;
|
||||
|
||||
export const DEFAULT_PROGRESS_DRAFT_INITIAL_DELAY_MS = 5_000;
|
||||
const DEFAULT_PROGRESS_DRAFT_MAX_LINE_CHARS = 72;
|
||||
|
||||
const NON_WORK_PROGRESS_TOOL_NAMES = new Set([
|
||||
"message",
|
||||
@@ -537,6 +538,52 @@ export function resolveChannelProgressDraftMaxLines(
|
||||
return configured && configured > 0 ? configured : defaultValue;
|
||||
}
|
||||
|
||||
function sliceCodePoints(value: string, start: number, end?: number): string {
|
||||
return Array.from(value).slice(start, end).join("");
|
||||
}
|
||||
|
||||
function compactProgressLineDetail(detail: string, maxChars: number): string {
|
||||
const chars = Array.from(detail);
|
||||
if (chars.length <= maxChars) {
|
||||
return detail;
|
||||
}
|
||||
if (maxChars <= 1) {
|
||||
return "…";
|
||||
}
|
||||
const keepStart = Math.max(1, Math.ceil((maxChars - 1) * 0.45));
|
||||
const keepEnd = Math.max(1, maxChars - keepStart - 1);
|
||||
const rawStart = chars.slice(0, keepStart).join("").trimEnd();
|
||||
const start =
|
||||
rawStart.length > 8 && /\s+\S+$/.test(rawStart) ? rawStart.replace(/\s+\S+$/, "") : rawStart;
|
||||
return `${start}…${chars.slice(-keepEnd).join("").trimStart()}`;
|
||||
}
|
||||
|
||||
function compactChannelProgressDraftLine(line: string, maxChars: number): string {
|
||||
const normalized = line.replace(/\s+/g, " ").trim();
|
||||
if (!normalized) {
|
||||
return "";
|
||||
}
|
||||
const chars = Array.from(normalized);
|
||||
if (chars.length <= maxChars) {
|
||||
return normalized;
|
||||
}
|
||||
if (maxChars <= 1) {
|
||||
return "…";
|
||||
}
|
||||
|
||||
const splitIndex = normalized.indexOf(": ");
|
||||
if (splitIndex > 0) {
|
||||
const prefix = normalized.slice(0, splitIndex + 2);
|
||||
const prefixChars = Array.from(prefix).length;
|
||||
const detailLimit = maxChars - prefixChars;
|
||||
if (detailLimit >= 8) {
|
||||
return `${prefix}${compactProgressLineDetail(normalized.slice(splitIndex + 2), detailLimit)}`;
|
||||
}
|
||||
}
|
||||
|
||||
return `${sliceCodePoints(normalized, 0, maxChars - 1).trimEnd()}…`;
|
||||
}
|
||||
|
||||
export function formatChannelProgressDraftText(params: {
|
||||
entry?: StreamingCompatEntry | null;
|
||||
lines: string[];
|
||||
@@ -554,7 +601,7 @@ export function formatChannelProgressDraftText(params: {
|
||||
const formatLine = params.formatLine ?? ((line: string) => line);
|
||||
const bullet = params.bullet ?? "•";
|
||||
const lines = params.lines
|
||||
.map((line) => line.replace(/\s+/g, " ").trim())
|
||||
.map((line) => compactChannelProgressDraftLine(line, DEFAULT_PROGRESS_DRAFT_MAX_LINE_CHARS))
|
||||
.filter((line) => line.length > 0)
|
||||
.slice(-maxLines)
|
||||
.map((line) =>
|
||||
|
||||
Reference in New Issue
Block a user