fix: seven reported defects in the 0.10.0 surface - #301
Merged
Conversation
Every one reproduced first from the report's own test, unchanged, before anything was edited; each fix carries the reproduction as a regression test plus the extra coverage its issue asked for. - to_asciicast dropped the newline that scrolled every frame. to_ansi ends each row with one, the bottom row included — right for a file, wrong for a repaint. The test now replays each exported event into a terminal of the recorded size and compares it to the frame it came from, which is what the old shape-only assertion could not see. (#295) - Screen::parse splits grid from metadata by the header's row count instead of hunting a `styles:` marker, because a grid can contain that word and a snapshot of one came back blank. The single input that cannot be read both ways — a hand-trimmed grid carrying a styles block — resolves as content, stated in the rustdoc: a wrong row shows up in a diff, a dropped one does not. (#296) - A combining mark after a wide character attaches to the cell that owns the glyph rather than to its continuation half, which holds no text. (#297) - A hidden cursor's position is no longer part of "the same picture", for ScreenDiff::is_empty and wait_stable alike: it draws nothing and the text format does not record it, so a screen differed from its own snapshot with nothing visible behind it. Visibility, and a visible cursor's position, still count. (#298) - parse_color validates six ASCII hex digits before slicing. `#a€bc` is six bytes, so the length check passed and the pair slice landed inside a character — an unwind out of the function whose whole job is returning Error::Parse, in a parser the CLI shares. (#299) - find_all and the masks now share one multi-row match engine. mask_matching is documented as matching "the way find_all matches", but ran its matcher per row, where a newline can never appear: it reported a row-spanning needle and then left it on screen, which is the one failure a mask exists to prevent. Extracting the engine is what stops the two drifting again. (#300) - form-echo and ratatui-app register crossterm's SIGWINCH listener before drawing the frame a test synchronizes on. A resize landing before the first event::read() was lost for good — SIGWINCH's default disposition is ignore — and wait_frame then spent a full deadline on an application that had never heard. resize-echo already guarded this; the comment there named the mechanism exactly. Found by the stress workflow on macOS at one thread. (#292) Also corrects the skill: it showed mask_matching("0123456789", '#') as "every digit anywhere", which reads a literal-substring API as a character set. Compiling a snippet does not check what its comment claims. Closes #295 Closes #296 Closes #297 Closes #298 Closes #299 Closes #300 Closes #292 Signed-off-by: Vyncint Ng <115854244+vyncint@users.noreply.github.com>
This file contains hidden or bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Sign up for free
to join this conversation on GitHub.
Already have an account?
Sign in to comment
Add this suggestion to a batch that can be applied as a single commit.This suggestion is invalid because no changes were made to the code.Suggestions cannot be applied while the pull request is closed.Suggestions cannot be applied while viewing a subset of changes.Only one suggestion per line can be applied in a batch.Add this suggestion to a batch that can be applied as a single commit.Applying suggestions on deleted lines is not supported.You must change the existing code in this line in order to create a valid suggestion.Outdated suggestions cannot be applied.This suggestion has been applied or marked resolved.Suggestions cannot be applied from pending reviews.Suggestions cannot be applied on multi-line comments.Suggestions cannot be applied while the pull request is queued to merge.Suggestion cannot be applied right now. Please check back later.
Every issue was reproduced first, from the report's own test unchanged, before anything was edited — all six filed reports were accurate:
["MIDDLE","BOTTOM",""]vs["TOP","MIDDLE","BOTTOM"]to_asciicastdrops the trailing newline that scrolled every frameParse("line 2: '\u{301}' has no character to combine with")(1,2,false)vs(0,0,false)end byte index 2 is not a char boundaryfind_allreported it, the mask left itfind_alland the masks share one multi-row engine#292 turned out to be diagnosable after all.
resize-echoalready carried this exact guard, with a comment naming the mechanism: crossterm registers its SIGWINCH listener on the firstevent::read(), so a resize landing between the first draw and that call is lost for good — SIGWINCH's default disposition is ignore.form-echoand myratatui-appnever got it. A fixture must not announce readiness before it can receive what a test is about to send.hello-tuineeds nothing (it handles no resize).#300 was fixed by extraction, not duplication. The rustdoc promises find_all semantics, so the two now literally share
for_each_multirow_match— that is what stops them drifting apart again.#296 has a stated policy for the one ambiguous input (a hand-trimmed grid that also carries a styles block): content wins, and the rustdoc says why — a wrong row of text is visible in a diff, a silently dropped one is not. One existing unit test relied on the old lenient split and was rewritten around realistic
with_styles()output.Also corrects the skill, which showed
mask_matching("0123456789", '#')as "every digit anywhere" — reading a literal-substring API as a character set. The snippet compiled; its comment was wrong, whichcheck-skill-snippets.shcannot catch.Gates: fmt, clippy ×6 incl. Windows cross-target, docs ×2, msrv, deny, zizmor, gates-listed, skill snippets. 513 tests pass.
cargo-semver-checksagainst 0.10.0: no semver update required, so this is a clean patch.Closes #295, closes #296, closes #297, closes #298, closes #299, closes #300, closes #292