123123213weqw opened a new pull request, #5730:
URL: https://github.com/apache/rocketmq-dashboard/pull/5730
## Problem / Evidence
`normalizeAiMarkdown` (`web/src/pages/ai/render/markdown.ts`) repairs model
markdown before `react-markdown` renders it, and its doc promises "well-formed
input comes back unchanged". Two of its repairs break that promise:
1. **Every well-formed ATX heading of level ≥ 2 is corrupted.** The heading
pass is `/^(#{1,6})(?=\S)/gm`: on `## heading` the greedy `#{1,6}` takes both
hashes, the lookahead sees the space and fails, and the engine **backtracks to
a single `#`** whose lookahead now sees the second `#` — a match. The
replacement rewrites the line to `# # heading` (verified: `'## heading'` → `'#
# heading'`, `'### heading'` → `'## # heading'`). Every assistant answer that
uses a real level-2+ heading renders it as a deeper heading with a stray `#` in
the text.
2. **Thematic breaks and setext underlines are rewritten into bullets.** The
bullet pass `/^([-+*])(?=\S)/gm` fires on the first dash of `---`: a horizontal
rule becomes `- --`, and a setext heading underline (`标题\n---`) becomes a
bullet under the title (verified: `'---'` → `'- --'`, `'***'` → `'* **'`).
## Root cause / Fix
- Headings: require the marker run to be maximal — `(?=[^\s#])` instead of
`(?=\S)`, so a marker followed by another `#` never matches and `##结论` still
gets its space.
- Bullets: add a negative lookahead `(?!\1\1)` so a run of three or more of
the same marker (thematic break / setext underline) is left alone while `-第一项`
is still repaired.
## Tests
- New `src/pages/ai/render/__tests__/markdown.test.ts`: the repair cases
(`##结论`, `-第一项`, fence info strings), idempotence over a well-formed document,
the heading corruption cases (`## heading` / `### heading` / `###### heading`),
and the thematic-break / setext cases. The heading and break cases fail on the
pre-fix code.
- `npx vitest run src/pages/ai` → 198/198 passed; `npx vitest run
src/pages/ai/components` → 79/79 passed; `npx tsc --noEmit -p
tsconfig.app.json` clean; eslint on touched files clean.
## Risk
Low: the function still only inserts whitespace; the two guards exclude
inputs the repair was never meant to touch.
--
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.
To unsubscribe, e-mail: [email protected]
For queries about this service, please contact Infrastructure at:
[email protected]