From baec487a21f15f9dfc4065a3a96a163e612ff222 Mon Sep 17 00:00:00 2001 From: t8y2 <1156263951@qq.com> Date: Wed, 12 Aug 2026 14:46:17 +0000 Subject: [PATCH] fix(data-grid): show first nonblank cell preview line Closes #5977 --- .../lib/__tests__/dataGrid/cellValue.spec.ts | 14 +++++++++++++ apps/desktop/src/lib/dataGrid/cellValue.ts | 21 +++++++++++++++++-- packages/app-tests/dataGridDetail.test.ts | 19 +++++++++++++++++ 3 files changed, 52 insertions(+), 2 deletions(-) diff --git a/apps/desktop/src/lib/__tests__/dataGrid/cellValue.spec.ts b/apps/desktop/src/lib/__tests__/dataGrid/cellValue.spec.ts index 9518ce0b70..a5e7cd0e7b 100644 --- a/apps/desktop/src/lib/__tests__/dataGrid/cellValue.spec.ts +++ b/apps/desktop/src/lib/__tests__/dataGrid/cellValue.spec.ts @@ -6,5 +6,19 @@ describe("firstLineCellDisplayValue", () => { expect(firstLineCellDisplayValue("111\n222")).toBe("111"); expect(firstLineCellDisplayValue("111\r\n222")).toBe("111"); expect(firstLineCellDisplayValue("111\r222")).toBe("111"); + expect(firstLineCellDisplayValue("single line")).toBe("single line"); + }); + + it("skips leading blank lines without stripping content indentation", () => { + expect(firstLineCellDisplayValue("\nINNODB MONITOR OUTPUT\nbody")).toBe("INNODB MONITOR OUTPUT"); + expect(firstLineCellDisplayValue("\r\nINNODB MONITOR OUTPUT\r\nbody")).toBe("INNODB MONITOR OUTPUT"); + expect(firstLineCellDisplayValue("\rINNODB MONITOR OUTPUT\rbody")).toBe("INNODB MONITOR OUTPUT"); + expect(firstLineCellDisplayValue(" \n indented content\nbody")).toBe(" indented content"); + }); + + it("preserves values that do not contain a content line", () => { + expect(firstLineCellDisplayValue("")).toBe(""); + expect(firstLineCellDisplayValue(" ")).toBe(" "); + expect(firstLineCellDisplayValue("\n\r\n \r")).toBe("\n\r\n \r"); }); }); diff --git a/apps/desktop/src/lib/dataGrid/cellValue.ts b/apps/desktop/src/lib/dataGrid/cellValue.ts index b61647b72e..ef205444ef 100644 --- a/apps/desktop/src/lib/dataGrid/cellValue.ts +++ b/apps/desktop/src/lib/dataGrid/cellValue.ts @@ -11,8 +11,25 @@ export function displayCellValue(value: CellValue): string { } export function firstLineCellDisplayValue(value: string): string { - const lineBreakIndex = value.search(/\r\n|\r|\n/); - return lineBreakIndex === -1 ? value : value.slice(0, lineBreakIndex); + const lineBreakPattern = /\r\n|\r|\n/g; + const firstLineBreak = lineBreakPattern.exec(value); + if (!firstLineBreak) return value; + + const firstLine = value.slice(0, firstLineBreak.index); + if (/\S/u.test(firstLine)) return firstLine; + + let lineStart = lineBreakPattern.lastIndex; + + while (lineStart <= value.length) { + const lineBreak = lineBreakPattern.exec(value); + const lineEnd = lineBreak?.index ?? value.length; + const line = value.slice(lineStart, lineEnd); + if (/\S/u.test(line)) return line; + if (!lineBreak) return value; + lineStart = lineBreakPattern.lastIndex; + } + + return value; } export function limitDataGridCellDisplay(value: string, maxLength = DATA_GRID_CELL_DISPLAY_MAX_LENGTH): string { diff --git a/packages/app-tests/dataGridDetail.test.ts b/packages/app-tests/dataGridDetail.test.ts index 4885600e40..544b6eceed 100644 --- a/packages/app-tests/dataGridDetail.test.ts +++ b/packages/app-tests/dataGridDetail.test.ts @@ -53,6 +53,25 @@ test("buildDataGridCellDetail preserves full value metadata", () => { }); }); +test("buildDataGridCellDetail preserves a leading newline in the full value", () => { + const status = "\n=====================================\nINNODB MONITOR OUTPUT\nbody"; + const detail = buildDataGridCellDetail({ + rowIndex: 0, + rowId: 1, + row: [status], + columns: ["Status"], + columnIndex: 0, + displayValue: (value) => String(value), + isEditable: false, + }); + + assert.equal(detail?.value, status); + assert.equal(detail?.rawValue, status); + assert.equal(detail?.rawValuePreview, status); + assert.equal(detail?.displayValue, status); + assert.equal(detail?.displayValuePreview, status); +}); + test("buildDataGridCellDetail reports image preview URLs", () => { const detail = buildDataGridCellDetail({ rowIndex: 0,