Skip to content

feat(table): add configurable table width export mode#888

Merged
cycleccc merged 1 commit into
masterfrom
chore/triage-issue-885
May 26, 2026
Merged

feat(table): add configurable table width export mode#888
cycleccc merged 1 commit into
masterfrom
chore/triage-issue-885

Conversation

@cycleccc

@cycleccc cycleccc commented May 26, 2026

Copy link
Copy Markdown
Collaborator

Summary

This PR adds a configurable table width export strategy and keeps backward compatibility by default.

  • Added MENU_CONF.insertTable.widthExportMode with two modes:
    • explicit (default, legacy-compatible)
    • adaptive (preserve width:auto on export)
  • Kept default behavior as explicit to avoid breaking existing integrations.
  • Added regression tests for both modes.
  • Added changeset.

Closes #885

Why

Issue #885 reports that imported width:auto; table-layout: fixed tables become fixed pixel width after export. Some users expect auto width to be preserved, while others rely on explicit pixel-width export. This PR supports both via config.

Behavior

  • Default (explicit): unchanged behavior.
  • Optional (adaptive): when table model width is auto, export keeps width:auto instead of converting from columnWidths to px.

Risk

  • Low risk for existing users: default remains explicit.
  • Moderate risk only for users who opt into adaptive (changed export contract by configuration).

Rollback

  • Safe rollback path:
    • Runtime: set MENU_CONF.insertTable.widthExportMode = 'explicit'.
    • Code rollback: revert this PR commit.

Validation

  • pnpm --filter @wangeditor-next/editor exec vitest run __tests__/create.test.ts -t "table width|explicit mode|adaptive mode|colgroup widths|by default" --reporter=dot
  • pnpm --filter @wangeditor-next/table-module exec vitest run __tests__/elem-to-html.test.ts --reporter=dot
  • pnpm --filter @wangeditor-next/table-module exec vitest run __tests__/parse-html.test.ts -t "colgroup widths|auto height|class mode attrs|width 100%" --reporter=dot
  • pnpm exec eslint packages/core/src/config/interface.ts packages/editor/__tests__/create.test.ts packages/table-module/src/module/elem-to-html.ts packages/table-module/src/module/menu/index.ts
  • pnpm turbo build --filter=@wangeditor-next/table-module --filter=@wangeditor-next/editor

Summary by CodeRabbit

  • New Features
    • Table width export behavior is now configurable with two modes: adaptive (preserves flexible width:auto styling) and explicit (applies computed fixed widths). Default is explicit for backward compatibility.

Review Change Stack

@changeset-bot

changeset-bot Bot commented May 26, 2026

Copy link
Copy Markdown

🦋 Changeset detected

Latest commit: e3cd174

The changes in this PR will be included in the next version bump.

This PR includes changesets to release 22 packages
Name Type
@wangeditor-next/core Patch
@wangeditor-next/editor Patch
@wangeditor-next/table-module Patch
@wangeditor-next/basic-modules Patch
@wangeditor-next/code-highlight Patch
@wangeditor-next/list-module Patch
@wangeditor-next/upload-image-module Patch
@wangeditor-next/video-module Patch
@wangeditor-next/yjs Patch
@wangeditor-next/demo-react Patch
@wangeditor-next/demo-vue3 Patch
@wangeditor-next/demo-yjs-react Patch
@wangeditor-next/demo-yjs-vue3 Patch
@wangeditor-next/plugin-attachment Patch
@wangeditor-next/plugin-ctrl-enter Patch
@wangeditor-next/plugin-float-image Patch
@wangeditor-next/plugin-formula Patch
@wangeditor-next/plugin-link-card Patch
@wangeditor-next/plugin-markdown Patch
@wangeditor-next/plugin-mention Patch
@wangeditor-next/yjs-for-react Patch
@wangeditor-next/yjs-for-vue Patch

Not sure what this means? Click here to learn what changesets are.

Click here if you're a maintainer who wants to add another changeset to this PR

@coderabbitai

coderabbitai Bot commented May 26, 2026

Copy link
Copy Markdown
Contributor
📝 Walkthrough

Walkthrough

This PR introduces a new insertTable.widthExportMode configuration feature that allows editors to choose between adaptive (preserves width: auto on export) and explicit (uses fixed widths) table width behavior. The feature defaults to explicit for backward compatibility, includes menu configuration, updates width export logic, and adds test coverage.

Changes

Table Width Export Mode Feature

Layer / File(s) Summary
Configuration Type Contract
packages/core/src/config/interface.ts
New exported TableWidthExportMode type with 'adaptive' | 'explicit' values; IInsertTableConfig extended with widthExportMode field.
Menu Configuration Defaults
packages/table-module/src/module/menu/index.ts
insertTableMenuConf.config object added with sizing defaults (minWidth, minRowHeight) and widthExportMode initialized to 'explicit'.
Width Export Logic Implementation
packages/table-module/src/module/elem-to-html.ts
getTableWidthExportMode() reads editor config (defaults to 'explicit'); getExportTableWidth() returns 'auto' in adaptive mode or computed fixed width in explicit mode; tableToHtml() passes editor context to width calculation.
Test Coverage & Release Documentation
packages/editor/__tests__/create.test.ts, .changeset/calm-news-prove.md
New test validates adaptive mode preserves width: auto with fixed layout and colgroup structure; existing explicit mode test updated; changeset documents feature availability.

Estimated code review effort

🎯 2 (Simple) | ⏱️ ~12 minutes

Possibly related PRs

  • wangeditor-next/wangEditor-next#83: Both PRs modify packages/table-module/src/module/elem-to-html.ts to change how table width/colgroup export is computed (main PR adds widthExportMode-driven getExportTableWidth logic; retrieved PR adjusts tableToHtml/width handling using columnWidths).
  • wangeditor-next/wangEditor-next#42: The retrieved PR fixes HTML paste parsing to initialize columnWidths, which the main PR's table HTML export code (getExportTableWidth/tableToHtml) uses to compute exported table width in non-adaptive mode.
  • wangeditor-next/wangEditor-next#795: Both PRs modify the table HTML width export logic in packages/table-module/src/module/elem-to-html.ts (and related getHtml/tableToHtml tests) to ensure exported fixed-layout tables produce explicit/preserved column-based widths rather than auto.

Poem

🐰 A table takes many shapes in the flow,
Some wide, some tight, now adaptive we go!
width: auto dances, or fixed widths stay—
Choose your mode, let the config say! 🎯📋

🚥 Pre-merge checks | ✅ 4 | ❌ 1

❌ Failed checks (1 warning)

Check name Status Explanation Resolution
Docstring Coverage ⚠️ Warning Docstring coverage is 0.00% which is insufficient. The required threshold is 80.00%. Write docstrings for the functions missing them to satisfy the coverage threshold.
✅ Passed checks (4 passed)
Check name Status Explanation
Title check ✅ Passed The title clearly and concisely summarizes the main feature addition: a configurable table width export mode, which directly matches the core changeset.
Description check ✅ Passed The PR description covers all major sections from the template including summary, implementation approach, testing details, validation steps, and checklist items, though some template sections are absent.
Linked Issues check ✅ Passed The PR successfully implements the objective from issue #885: supporting configurable table width export via the new widthExportMode setting with 'adaptive' and 'explicit' modes, preserving auto width behavior when configured.
Out of Scope Changes check ✅ Passed All code changes are directly related to implementing the configurable table width export feature; no out-of-scope modifications were detected.

✏️ Tip: You can configure your own custom pre-merge checks in the settings.

✨ Finishing Touches
📝 Generate docstrings
  • Create stacked PR
  • Commit on current branch
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch chore/triage-issue-885

Warning

There were issues while running some tools. Please review the errors and either fix the tool's configuration or disable the tool if it's a critical failure.

🔧 ESLint

If the error stems from missing dependencies, add them to the package.json file. For unrecoverable errors (e.g., due to private dependencies), disable the tool in the CodeRabbit configuration.

packages/core/src/config/interface.ts

ESLint skipped: missing config or dependency (missing-dependency). The ESLint configuration references a package that is not available in the sandbox.

packages/editor/__tests__/create.test.ts

ESLint skipped: the ESLint configuration for this file references a package that is not available in the sandbox.

packages/table-module/src/module/elem-to-html.ts

ESLint skipped: the ESLint configuration for this file references a package that is not available in the sandbox.

  • 1 others

Thanks for using CodeRabbit! It's free for OSS, and your support helps us grow. If you like it, consider giving us a shout-out.

❤️ Share

Comment @coderabbitai help to get the list of available commands and usage tips.

@cycleccc cycleccc force-pushed the chore/triage-issue-885 branch from e23c48d to e3cd174 Compare May 26, 2026 06:25

@chatgpt-codex-connector chatgpt-codex-connector Bot left a comment

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

💡 Codex Review

Here are some automated review suggestions for this pull request.

Reviewed commit: e23c48d533

ℹ️ About Codex in GitHub

Your team has set up Codex to review pull requests in this repo. Reviews are triggered when you

  • Open a pull request for review
  • Mark a draft as ready
  • Comment "@codex review".

If Codex has suggestions, it will comment; otherwise it will react with 👍.

Codex can also answer questions or update the PR. Try commenting "@codex address that feedback".


const menuConf = editor.getMenuConfig('insertTable') as { widthExportMode?: TableWidthExportMode }

return menuConf?.widthExportMode === 'explicit' ? 'explicit' : 'adaptive'

Copy link
Copy Markdown

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

P2 Badge Default missing widthExportMode to explicit

Treat missing/unknown widthExportMode as 'explicit' here; the current fallback returns 'adaptive' for any non-'explicit' value, including when editor.getMenuConfig('insertTable') returns {} or a malformed config. In those cases, tables with width: auto + columnWidths stop exporting pixel widths and unexpectedly emit width:auto, which breaks the commit’s backward-compatibility guarantee for default behavior.

Useful? React with 👍 / 👎.

@coderabbitai coderabbitai Bot left a comment

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

Actionable comments posted: 2

Caution

Some comments are outside the diff and can’t be posted inline due to platform limitations.

⚠️ Outside diff range comments (1)
packages/editor/__tests__/create.test.ts (1)

188-236: 🛠️ Refactor suggestion | 🟠 Major | ⚡ Quick win

Round-trip coverage is still incomplete for this serialization change.

Please add explicit checks for toHtml(parseHtml(html)) and the explicit-mode round-trip path
alongside the current setHtml(getHtml()) adaptive assertion.

As per coding guidelines, "**/*.test.{ts,tsx}: Test round-trip export/import ... across render/toHtml/parseHtml paths, and with setHtml(getHtml())/toHtml(parseHtml(html)) when modifying serialization or styles".

🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/editor/__tests__/create.test.ts` around lines 188 - 236, Add
assertions that exercise the toHtml(parseHtml(html)) path and the explicit-mode
round-trip in addition to the existing setHtml(getHtml()) adaptive checks: call
the parser/render path (use parseHtml(html) and the toHtml helper or equivalent)
and assert its output contains the same expected table style/colgroup strings,
and for the explicit width case recreate the editor with
MENU_CONF.insertTable.widthExportMode set to 'explicit' (or use
customCreateEditor({ html, config: { MENU_CONF: { insertTable: {
widthExportMode: 'explicit' } } } })) then assert both toHtml(parseHtml(html))
and setHtml(getHtml()) round-trips produce the expected 'style="width:
200px;table-layout: fixed;' and the colgroup HTML; keep the existing adaptive
test unchanged but add these extra expectations for round-trip coverage.
🤖 Prompt for all review comments with AI agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

Inline comments:
In `@packages/core/src/config/interface.ts`:
- Around line 118-127: The new widthExportMode property was added to
IInsertTableConfig but the runtime and tests expect it on the menu config key
used by MENU_CONF.insertTable (IMenuConfig currently maps it to insertTableRow),
so remove widthExportMode from IInsertTableConfig and instead add/align it to
the menu config type that represents MENU_CONF.insertTable (update
IMenuConfig/ISingleMenuConfig mapping or the explicit insertTable type so that
IMenuConfig.insertTable includes widthExportMode); reference IInsertTableConfig,
IMenuConfig, ISingleMenuConfig, insertTableRow, and insertTable to locate and
adjust the types accordingly.

In `@packages/table-module/src/module/elem-to-html.ts`:
- Around line 22-30: The current getTableWidthExportMode function treats any
non-'explicit' value (including undefined) as 'adaptive'; change the logic so
missing/invalid config falls back to 'explicit' instead. In
getTableWidthExportMode, read menuConf?.widthExportMode and return 'adaptive'
only when it is explicitly 'adaptive' (e.g., menuConf?.widthExportMode ===
'adaptive' ? 'adaptive' : 'explicit'); keep checks for editor and getMenuConfig
as-is and update the return expression accordingly.

---

Outside diff comments:
In `@packages/editor/__tests__/create.test.ts`:
- Around line 188-236: Add assertions that exercise the toHtml(parseHtml(html))
path and the explicit-mode round-trip in addition to the existing
setHtml(getHtml()) adaptive checks: call the parser/render path (use
parseHtml(html) and the toHtml helper or equivalent) and assert its output
contains the same expected table style/colgroup strings, and for the explicit
width case recreate the editor with MENU_CONF.insertTable.widthExportMode set to
'explicit' (or use customCreateEditor({ html, config: { MENU_CONF: {
insertTable: { widthExportMode: 'explicit' } } } })) then assert both
toHtml(parseHtml(html)) and setHtml(getHtml()) round-trips produce the expected
'style="width: 200px;table-layout: fixed;' and the colgroup HTML; keep the
existing adaptive test unchanged but add these extra expectations for round-trip
coverage.
🪄 Autofix (Beta)

Fix all unresolved CodeRabbit comments on this PR:

  • Push a commit to this branch (recommended)
  • Create a new PR with the fixes

ℹ️ Review info
⚙️ Run configuration

Configuration used: defaults

Review profile: CHILL

Plan: Pro

Run ID: 7578b7d8-a29f-4af6-a5be-d51dcde54398

📥 Commits

Reviewing files that changed from the base of the PR and between 68a65d3 and e3cd174.

📒 Files selected for processing (5)
  • .changeset/calm-news-prove.md
  • packages/core/src/config/interface.ts
  • packages/editor/__tests__/create.test.ts
  • packages/table-module/src/module/elem-to-html.ts
  • packages/table-module/src/module/menu/index.ts

Comment on lines 118 to +127
interface IInsertTableConfig {
minWidth: number;
minRowHeight: number;
tableHeader: {
selected: boolean;
};
tableFullWidth: {
selected: boolean;
}
};
widthExportMode: TableWidthExportMode;

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

widthExportMode is typed on the wrong menu config contract key.

widthExportMode was added to IInsertTableConfig, but IMenuConfig currently binds that type to
insertTableRow, while runtime/test usage reads MENU_CONF.insertTable. This makes the new public
type contract inaccurate and hides the real config shape behind ISingleMenuConfig’s index signature.

Suggested contract alignment
 interface IMenuConfig {
-  insertTable: ISingleMenuConfig;
+  insertTable: IInsertTableConfig;
   deleteTable: ISingleMenuConfig;
-  insertTableRow: IInsertTableConfig;
+  insertTableRow: ISingleMenuConfig;
   deleteTableRow: ISingleMenuConfig;
   ...
 }
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/core/src/config/interface.ts` around lines 118 - 127, The new
widthExportMode property was added to IInsertTableConfig but the runtime and
tests expect it on the menu config key used by MENU_CONF.insertTable
(IMenuConfig currently maps it to insertTableRow), so remove widthExportMode
from IInsertTableConfig and instead add/align it to the menu config type that
represents MENU_CONF.insertTable (update IMenuConfig/ISingleMenuConfig mapping
or the explicit insertTable type so that IMenuConfig.insertTable includes
widthExportMode); reference IInsertTableConfig, IMenuConfig, ISingleMenuConfig,
insertTableRow, and insertTable to locate and adjust the types accordingly.

Comment on lines +22 to +30
function getTableWidthExportMode(editor?: IDomEditor): TableWidthExportMode {
if (!editor || typeof editor.getMenuConfig !== 'function') {
return 'explicit'
}

const menuConf = editor.getMenuConfig('insertTable') as { widthExportMode?: TableWidthExportMode }

return menuConf?.widthExportMode === 'explicit' ? 'explicit' : 'adaptive'
}

Copy link
Copy Markdown
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

⚠️ Potential issue | 🟠 Major | ⚡ Quick win

Default fallback is inverted to adaptive when config is missing/undefined.

This function currently defaults to adaptive for any non-explicit value. That breaks the stated
backward-compatible default. Missing/invalid config should resolve to explicit.

Suggested fix
-  return menuConf?.widthExportMode === 'explicit' ? 'explicit' : 'adaptive'
+  return menuConf?.widthExportMode === 'adaptive' ? 'adaptive' : 'explicit'
🤖 Prompt for AI Agents
Verify each finding against current code. Fix only still-valid issues, skip the
rest with a brief reason, keep changes minimal, and validate.

In `@packages/table-module/src/module/elem-to-html.ts` around lines 22 - 30, The
current getTableWidthExportMode function treats any non-'explicit' value
(including undefined) as 'adaptive'; change the logic so missing/invalid config
falls back to 'explicit' instead. In getTableWidthExportMode, read
menuConf?.widthExportMode and return 'adaptive' only when it is explicitly
'adaptive' (e.g., menuConf?.widthExportMode === 'adaptive' ? 'adaptive' :
'explicit'); keep checks for editor and getMenuConfig as-is and update the
return expression accordingly.

@cycleccc cycleccc merged commit 8a8ae86 into master May 26, 2026
8 checks passed
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

None yet

Projects

None yet

Development

Successfully merging this pull request may close these issues.

关于表格列宽显示及无法调节问题

1 participant