Refine terminal history scrolling and job failure summaries
This commit is contained in:
@@ -15,7 +15,7 @@ type TerminalQuickCommand = { label: string; command: string; hint: string };
|
||||
const terminalBridgeResultPollMs = 1000;
|
||||
const terminalBridgeResultPollAttempts = 30;
|
||||
const liveLogHistoryWindow = 100;
|
||||
const terminalHistoryWindow = 10000;
|
||||
const terminalInitialHistoryWindow = 500;
|
||||
const maxLogEntries = 500;
|
||||
const maxTerminalLines = 10000;
|
||||
const terminalQuickCommandCatalog: Record<string, TerminalQuickCommand[]> = {
|
||||
@@ -212,6 +212,7 @@ export function ServerManagementTerminalDrawer({ open, serverId, serverName, plu
|
||||
const [followLatest, setFollowLatest] = useState(true);
|
||||
const outputRef = useRef<HTMLDivElement>(null);
|
||||
const followLatestRef = useRef(true);
|
||||
const initialHistoryPendingRef = useRef(false);
|
||||
const quickCommands = useMemo(() => terminalQuickCommandsForPlugin(pluginId), [pluginId]);
|
||||
const supportsCommands = quickCommands.length > 0;
|
||||
const terminalStreams = useMemo(() => streams.status === "ready" ? terminalRelevantStreams(streams.data) : [], [streams]);
|
||||
@@ -221,6 +222,20 @@ export function ServerManagementTerminalDrawer({ open, serverId, serverName, plu
|
||||
setLines((current) => mergeTerminalLines(current, incoming));
|
||||
}, []);
|
||||
|
||||
const lockTerminalFollow = useCallback(() => {
|
||||
followLatestRef.current = true;
|
||||
setFollowLatest(true);
|
||||
window.requestAnimationFrame(() => {
|
||||
const output = outputRef.current;
|
||||
if (output) output.scrollTop = output.scrollHeight;
|
||||
window.requestAnimationFrame(() => {
|
||||
const output = outputRef.current;
|
||||
if (output) output.scrollTop = output.scrollHeight;
|
||||
initialHistoryPendingRef.current = false;
|
||||
});
|
||||
});
|
||||
}, []);
|
||||
|
||||
const loadStreams = useCallback(async (showLoading = true) => {
|
||||
if (!open) return;
|
||||
if (showLoading) setStreams({ status: "loading" });
|
||||
@@ -238,6 +253,7 @@ export function ServerManagementTerminalDrawer({ open, serverId, serverName, plu
|
||||
setPending(false);
|
||||
setResult(null);
|
||||
setHistoryIndex(null);
|
||||
initialHistoryPendingRef.current = true;
|
||||
followLatestRef.current = true;
|
||||
setFollowLatest(true);
|
||||
setLines([terminalSystemLine("info", supportsCommands ? "连接平台日志推送,先补最近历史再实时追加。" : "该插件暂未声明可用的管理终端命令通道。", "SYSTEM")]);
|
||||
@@ -245,7 +261,7 @@ export function ServerManagementTerminalDrawer({ open, serverId, serverName, plu
|
||||
}, [loadStreams, open, supportsCommands]);
|
||||
|
||||
useEffect(() => {
|
||||
if (!open || !followLatestRef.current) return undefined;
|
||||
if (!open || initialHistoryPendingRef.current || !followLatestRef.current) return undefined;
|
||||
const frame = window.requestAnimationFrame(() => {
|
||||
const output = outputRef.current;
|
||||
if (output) output.scrollTop = output.scrollHeight;
|
||||
@@ -256,7 +272,7 @@ export function ServerManagementTerminalDrawer({ open, serverId, serverName, plu
|
||||
useEffect(() => {
|
||||
if (!open) return undefined;
|
||||
let ready = false;
|
||||
const events = platformApiClient.openServerLogEvents(serverId, { historyLimit: terminalHistoryWindow });
|
||||
const events = platformApiClient.openServerLogEvents(serverId, { historyLimit: terminalInitialHistoryWindow });
|
||||
events.addEventListener("stream", (event) => {
|
||||
const stream = parseLogStreamEvent(event);
|
||||
if (!stream) return;
|
||||
@@ -266,6 +282,7 @@ export function ServerManagementTerminalDrawer({ open, serverId, serverName, plu
|
||||
events.addEventListener("ready", () => {
|
||||
ready = true;
|
||||
setStreams((current) => current.status === "ready" ? current : { status: "ready", data: [] });
|
||||
lockTerminalFollow();
|
||||
});
|
||||
events.addEventListener("log", (event) => {
|
||||
const payload = parseServerLogEvent(event);
|
||||
@@ -279,7 +296,7 @@ export function ServerManagementTerminalDrawer({ open, serverId, serverName, plu
|
||||
if (!ready) setStreams({ status: "error", reason: "实时日志推送连接失败" });
|
||||
};
|
||||
return () => events.close();
|
||||
}, [appendLines, open, serverId]);
|
||||
}, [appendLines, lockTerminalFollow, open, serverId]);
|
||||
|
||||
function selectQuickCommand(item: TerminalQuickCommand) {
|
||||
setCommand(item.command);
|
||||
|
||||
Reference in New Issue
Block a user