Skip to content

sheet range set-style unmerges fully covered merged ranges despite style-only contract (v1.0.63) #1497

Open

Description

@dzshzx

Environment

DWS v1.0.63, commit 4cd5d05 (2026-10-03). Reproduced on 2026-10-13 with a newly created disposable Sheet containing only synthetic text.

Minimal trigger

Create a disposable Sheet and use nodeId and sheetId returned by create-with-data. No existing business Sheet is needed.

dws sheet create-with-data --name DWS-MERGE-REPRO --values '[["","SYNTHETIC_TITLE","","CONTROL"],["","SYNTHETIC_GUIDE","",""],["CONTROL","","",""]]' --format json
dws sheet merge-cells --node NODE_FROM_CREATE --sheet-id SHEET_FROM_CREATE --range B1:C1 --format json
dws sheet info --node NODE_FROM_CREATE --sheet-id SHEET_FROM_CREATE --format json
dws sheet range set-style --node NODE_FROM_CREATE --sheet-id SHEET_FROM_CREATE --range B1:C1 --font-weight bold --format json
dws sheet info --node NODE_FROM_CREATE --sheet-id SHEET_FROM_CREATE --format json
dws sheet range read --node NODE_FROM_CREATE --sheet-id SHEET_FROM_CREATE --range A1:D3 --format json

Before set-style, mergedRanges is ["B1:C1"]. The style call succeeds. Afterward, mergedRanges is [], while the values are unchanged and both cells have fontWeight=bold. One pre-existing merged block and one style-only write suffice.

The dry-run translates the write to set_cell_range with only nodeId, sheetId, rangeAddress, and cells=[[{cellStyles:{fontWeight:"bold"}},{cellStyles:{fontWeight:"bold"}}]]. It contains no value or explicit unmerge operation.

Expected behavior

Pure style writes should preserve existing merged ranges, or explicitly reject unsupported shapes without changing structure. The pinned source documents style-only writes as safe for merged cells:

// set-style / batch-set-style
//
// 方案 A(对齐飞书 +cells-set-style):样式统一走 set_cell_range 的 cellStyles 路径,
// 每个单元格产出 {"cellStyles":{...}}(不写值,保留原值);纯样式写入对合并单元格安全
// (底层 setComplexValues 仅对写值 cell 拦截合并冲突)。
and #L486-L492.

Isolation matrix

Before each case we restored B1:C1 and B2:C2 and read both structure and A1:D3 content. Each case contained one operation. Standalone and batch-update produced the same merge-preservation and value outcomes. Their error envelopes differ for the full merged-range value case: standalone returns MERGED_CELLS_CONFLICT, while batch-update returns stateServer.invalid_operation with MERGED_CELLS_CONFLICT as the cause. The standalone B1:C1 value case was separately reconfirmed on the same version with raw stdout/stderr, exit code, and complete before/after reads:

Operation Result Merges afterward
set-style B1:C1 success only B2:C2 remains
set-style B1 success both remain
set-style C1 success both remain
set-style D3 success both remain
range update B1:C1 with text cells MERGED_CELLS_CONFLICT both remain
range update B1 MERGED_CELLS_CONFLICT both remain
range update C1 MERGED_CELLS_CONFLICT both remain
range update D3 success both remain

A separate style-only B1:C2 write removes both merged blocks. Values remain intact throughout the style probes. All range reads reported hasMore=false. The batch variant used exactly one range set-style operation, ruling out interactions with other subcommands.

Temporary compatibility handling

After reading the original merge ranges and proving subordinate cells contain no unique values, a strict batch containing the style write followed by explicit merge-cells (B1:C2, mergeRows) restored both original merges. A subsequent info/range read verified both merges, all values, and the requested bold style. This is a caller workaround verified only on the disposable synthetic sample; the underlying merged-range preservation issue still needs correction.

Limits

The reproduction identifies the public operation and range shape that changes structure. Server-side implementation is not visible, so this report does not claim whether the final defect lies in CLI translation or the remote Sheet tool. No credentials, personnel records, internal document links, or original business payloads are included.

Activity

  1. dzshzx commented on Oct 13, 2026

    @dzshzx
    Author

    Clarification of the value-write rows in the isolation matrix: the error-envelope difference applies to all three merged targets, not only the full merged range.

    Value-write target Standalone sheet range update: error.server_error_code Single-operation sheet batch-update: error.server_error_code
    B1:C1 MERGED_CELLS_CONFLICT stateServer.invalid_operation
    B1 MERGED_CELLS_CONFLICT stateServer.invalid_operation
    C1 MERGED_CELLS_CONFLICT stateServer.invalid_operation

    For each batch case, the error message identifies MERGED_CELLS_CONFLICT as the cause. The issue body's Result column records the standalone error code for these three rows. Both invocation modes preserved the existing merges and cell values in the recorded before/after reads; their outer error codes are different.

    My previous body edit replaced “Standalone and batch-update gave identical outcomes” with a statement about matching merge-preservation and value outcomes, added the distinct error envelopes, and documented a separate same-version recheck of the standalone B1:C1 value write with captured stdout, stderr, exit code, and complete before/after reads. The phrase “for the full merged-range value case” was too narrow: the retained raw errors show the same envelope distinction for B1 and C1 as well. This comment clarifies all three rows; it does not report a new table write or a fix to the style-only unmerge issue.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Metadata

Metadata

Assignees

No one assigned

    Labels

    No labels
    No labels

    Type

    No type

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions