Skip to content

Tighten break Cow tests and test helpers - #81

Merged
leynos merged 21 commits into
mainfrom
codex/refactor-format_breaks-to-use-cowstr
Jun 1, 2026
Merged

Tighten break Cow tests and test helpers#81
leynos merged 21 commits into
mainfrom
codex/refactor-format_breaks-to-use-cowstr

Conversation

@leynos

@leynos leynos commented Jul 16, 2025

Copy link
Copy Markdown
Owner

Summary

  • assert the Cow variants returned by format_breaks so tests cover the borrowed-output optimisation directly
  • update the break-formatting Rustdoc example to show borrowed thematic break output
  • remove the redundant string_vec! helper and keep test helper lint suppressions item-scoped

Testing

  • make check-fmt
  • make lint
  • make test

https://chatgpt.com/codex/tasks/task_e_687837d741488322b8f005ad81122c27

@sourcery-ai

sourcery-ai Bot commented Jul 16, 2025

Copy link
Copy Markdown
Contributor

Reviewer's Guide

This PR refactors the format_breaks function to return Cow instead of String, reducing unnecessary cloning of unmodified lines, and updates all relevant callers and tests to accommodate the new return type while simplifying test data creation.

Class diagram for refactored format_breaks function and usage

classDiagram
    class format_breaks {
        +format_breaks(lines: &[String]) -> Vec<Cow<'_, str>>
    }
    class Cow {
        <<enum>>
        +Borrowed(&'a str)
        +Owned(String)
    }
    class process_lines {
        +process_lines(lines: &[String], opts: FormatOpts) -> Vec<String>
    }
    format_breaks --> Cow : returns Vec<Cow<'_, str>>
    process_lines --> format_breaks : calls
    process_lines --> Cow : converts Cow to String
Loading

File-Level Changes

Change Details Files
Refactored format_breaks to return Cow instead of String, reducing unnecessary cloning.
  • Changed format_breaks return type to Vec<Cow> to allow borrowing or owning as needed.
  • Replaced line cloning with Cow::Borrowed for unmodified lines and Cow::Owned for modified lines within format_breaks.
  • Updated all callers of format_breaks to handle Cow output, converting to String where necessary.
src/breaks.rs
src/main.rs
Simplified and updated tests to accommodate new Cow return type and streamlined test data creation.
  • Modified test assertions to convert Cow to String for comparison.
  • Simplified test input creation by removing unnecessary iterator and map calls.
src/breaks.rs
tests/integration.rs

Tips and commands

Interacting with Sourcery

  • Trigger a new review: Comment @sourcery-ai review on the pull request.
  • Continue discussions: Reply directly to Sourcery's review comments.
  • Generate a GitHub issue from a review comment: Ask Sourcery to create an
    issue from a review comment by replying to it. You can also reply to a
    review comment with @sourcery-ai issue to create an issue from it.
  • Generate a pull request title: Write @sourcery-ai anywhere in the pull
    request title to generate a title at any time. You can also comment
    @sourcery-ai title on the pull request to (re-)generate the title at any time.
  • Generate a pull request summary: Write @sourcery-ai summary anywhere in
    the pull request body to generate a PR summary at any time exactly where you
    want it. You can also comment @sourcery-ai summary on the pull request to
    (re-)generate the summary at any time.
  • Generate reviewer's guide: Comment @sourcery-ai guide on the pull
    request to (re-)generate the reviewer's guide at any time.
  • Resolve all Sourcery comments: Comment @sourcery-ai resolve on the
    pull request to resolve all Sourcery comments. Useful if you've already
    addressed all the comments and don't want to see them anymore.
  • Dismiss all Sourcery reviews: Comment @sourcery-ai dismiss on the pull
    request to dismiss all existing Sourcery reviews. Especially useful if you
    want to start fresh with a new review - don't forget to comment
    @sourcery-ai review to trigger a new review!

Customizing Your Experience

Access your dashboard to:

  • Enable or disable review features such as the Sourcery-generated pull request
    summary, the reviewer's guide, and others.
  • Change the review language.
  • Add, remove or edit custom review instructions.
  • Adjust other review settings.

Getting Help

@coderabbitai

coderabbitai Bot commented Jul 16, 2025

Copy link
Copy Markdown
Contributor

Review Change Stack

No actionable comments were generated in the recent review. 🎉

ℹ️ Recent review info
⚙️ Run configuration

Configuration used: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 6daf0b27-0cd6-4bc3-9216-910a7738bebc

📥 Commits

Reviewing files that changed from the base of the PR and between 94f6803 and 11ac066.

📒 Files selected for processing (2)
  • docs/developers-guide.md
  • docs/users-guide.md

Overview

This PR refactors format_breaks to return Vec<Cow<'_, str>> instead of Vec<String>, enabling borrowed slices for unchanged lines and synthesised thematic-break lines. It includes comprehensive test updates to verify borrowing semantics, reorganisation of test support infrastructure, and documentation updates for both library users and developers.

Key Changes

Core Functionality

  • format_breaks now returns Vec<Cow<'_, str>> where non-thematic-break lines borrow from input and synthesised thematic-break lines borrow from a shared static THEMATIC_BREAK_LINE buffer, eliminating forced heap allocations for unchanged content.

Test Infrastructure

  • Added assert_borrowed_value! and assert_borrowed_break! macros in src/breaks.rs and tests/breaks.rs to explicitly assert borrowing behaviour via pattern matching on Cow::Borrowed.
  • Reorganised test support modules under tests/support/ with explicit #[path = ...] declarations:
    • Introduced cli_args.rs (with run_cli_with_args helper)
    • Introduced cli_stdin.rs (with run_cli_with_stdin helper)
    • Introduced wrap_assertions.rs (with assert_wrapped_list_item and assert_wrapped_blockquote helpers)
    • Introduced fixtures.rs (with shared broken_table() fixture)
  • Converted multiple test functions from infallible to Result<(), Box<dyn std::error::Error>> for better error propagation.
  • Added property-based tests enforcing Cow borrowing invariants (via proptest upgraded from 1.6 to 1.11.0).
  • Added compile-time regression test via trybuild to verify the new allow_fixture_expansion_lints proc-macro attribute.

Proc-Macro Support

  • Introduced test-macros crate with allow_fixture_expansion_lints attribute that automatically emits #[allow(unused_braces, ...)] for fixture expansions.
  • Exported lines_vec! and include_lines! macros from tests/common/mod.rs via #[macro_export] for cross-binary visibility.

Documentation

  • Updated README.md, docs/users-guide.md, and docs/developers-guide.md to document the Vec<Cow<'_, str>> return type and borrowing strategy.
  • Added guidance on using .into_owned() for callers requiring owned Strings.
  • Updated CHANGELOG.md to document the breaking change.
  • Adjusted spelling throughout (standardised → standardized, synthesised → synthesized).
  • Updated documentation example in src/breaks.rs to reflect borrowed output.

Lint Management

  • Removed crate-level #![allow(unfulfilled_lint_expectations)].
  • Moved lint suppressions from macro declarations to #[macro_export] annotations for item-scoped visibility.

Testing & Verification

  • Extended property tests in src/breaks.rs to verify output length matches input, non-thematic outputs borrow from corresponding input strings, and thematic-break outputs consistently borrow from the static.
  • Added multithreaded stability test verifying thematic-break output pointer stability across threads via std::ptr::eq.
  • Strengthened existing integration tests (fenced-code, mixed-character, spaces/indent, tabs) to assert borrowing behaviour.
  • GitHub issue #342 opened to triage whether additional concurrent tests for LazyLock initialisation are warranted; reviewer confirmed all substantive items resolved.

Walkthrough

Refactor format_breaks to return Vec<Cow<'_, str>> so unchanged lines and synthetic thematic breaks can be borrowed. Update unit/property and integration tests to assert borrowing semantics. Add a test-macros proc-macro for fixture lint suppression, extract and export test helpers into tests/support, rewire tests to use them, and update docs and dev-dependencies.

Changes

format_breaks Cow allocation and test infrastructure

Layer / File(s) Summary
format_breaks returns Cow<'_, str> with borrowing assertions
src/breaks.rs, tests/breaks.rs
Updated format_breaks documentation example and unit/property tests to assert Cow::Borrowed for passthrough lines and thematic breaks. Added assert_borrowed_value! and assert_borrowed_break! macros and pointer-equality checks to validate borrowing invariants.
Proc-macro test-fixtures linting and macro exports
test-macros/Cargo.toml, test-macros/src/lib.rs, tests/common/mod.rs, tests/support/fixtures.rs, tests/compile.rs, tests/ui/allow_fixture_expansion_lints_pass.rs
Added test-macros proc-macro crate with allow_fixture_expansion_lints attribute. Replaced per-macro #[expect(...)] lint attributes with #[macro_export] for lines_vec! and include_lines!. Added a shared broken_table fixture and a trybuild UI test to validate the proc-macro compiles.
New test support helper modules
tests/support/cli_args.rs, tests/support/cli_stdin.rs, tests/support/wrap_assertions.rs
Introduced run_cli_with_args and run_cli_with_stdin helpers returning Result<Assert, Box<dyn Error>>, and assert_wrapped_list_item / assert_wrapped_blockquote helpers with backtick-run scanning to validate wrapping behaviour.
Update test module imports to use support structure
tests/cli.rs, tests/cli_fences.rs, tests/code_emphasis.rs, tests/parallel.rs, tests/table/mod.rs, tests/wrap/mod.rs, tests/wrap/*
Rewired test suites to import helpers from tests/support/* via explicit #[path = ...] modules, changed many tests to return Result and use ? with the new helpers, and adjusted a few unwrap sites for in-place CLI helpers.
Documentation updates and metadata changes
CHANGELOG.md, README.md, docs/developers-guide.md, docs/rust-testing-with-rstest-fixtures.md, Cargo.toml, docs/users-guide.md, tests/wrap/spanning_code_spans.rs
Documented breaking change (format_breaks now returns Cow), added developer-guide sections on test support layout and Cow allocation strategy, corrected fixture example macro syntax, bumped proptest dev-dependency, and fixed two spelling instances in tests.

Sequence Diagram(s)

(Changes are library return-type updates, test infra extraction, proc-macro addition and docs updates; no new multi-component runtime sequence diagram required.)

Possibly related issues

Possibly related PRs

  • leynos/mdtablefix#275 — Shares related rewiring of tests/cli_fences.rs and nested-fence test coverage.
  • leynos/axinite#18 — Adjusts lines_vec![] example formatting in docs (documentation-level overlap).

Poem

A borrowed line stays where it lived,
No heap allocations unforgiven.
Static underscores line up in a row,
Tests poke pointers to prove what they know —
Cow returns home, tidy and thrived. 🦬✨

🚥 Pre-merge checks | ✅ 5 | ❌ 15

❌ Failed checks (15 inconclusive)

Check name Status Explanation Resolution
Testing (Overall) ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
User-Facing Documentation ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Developer Documentation ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Module-Level Documentation ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Testing (Unit And Behavioural) ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Testing (Property / Proof) ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Testing (Compile-Time / Ui) ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Unit Architecture ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Domain Architecture ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Observability ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Security And Privacy ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Performance And Resource Use ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Concurrency And State ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Architectural Complexity And Maintainability ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
Rust Compiler Lint Integrity ❓ Inconclusive Repository clone failed, so this custom check could not run with code access. Retry the review run. If this persists, inspect pre-merge custom-check logs for infrastructure or agent runtime failures.
✅ Passed checks (5 passed)
Check name Status Explanation
Title check ✅ Passed The title 'Tighten break Cow tests and test helpers' directly describes the main changes: strengthening Cow-variant assertions in break tests and refactoring test helpers (removing string_vec!, making lint suppressions item-scoped, exporting macros).
Description check ✅ Passed The description relates directly to the changeset: asserts Cow variants in format_breaks tests, updates Rustdoc examples, removes string_vec! helper, and scopes lint suppressions—all present in the raw summary.
Docstring Coverage ✅ Passed Docstring coverage is 100.00% which is sufficient. The required threshold is 80.00%.
Linked Issues check ✅ Passed Check skipped because no linked issues were found for this pull request.
Out of Scope Changes check ✅ Passed Check skipped because no linked issues were found for this pull request.

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

✨ Finishing Touches
🧪 Generate unit tests (beta)
  • Create PR with unit tests
  • Commit unit tests in branch codex/refactor-format_breaks-to-use-cowstr

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

sourcery-ai[bot]

This comment was marked as resolved.

@leynos

leynos commented Jul 17, 2025

Copy link
Copy Markdown
Owner Author

@coderabbitai pause

@coderabbitai

coderabbitai Bot commented Jul 17, 2025

Copy link
Copy Markdown
Contributor
✅ Actions performed

Reviews paused.

@lodyai
lodyai Bot force-pushed the codex/refactor-format_breaks-to-use-cowstr branch from bfaaac2 to 547d7b5 Compare May 25, 2026 19:33
@leynos

leynos commented May 25, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai Have the following now been resolved?

Annul any requirements that violate the en-GB-oxendict spelling (-ize / -yse / -our) conventions (for example a request to replace "normalize" with "normalise" or "artefact" with "artifact"), or where the requirement unnecessarily increases cyclomatic complexity.

Please address the comments from this code review:
## Individual Comments

### Comment 1
<location> `src/breaks.rs:31` </location>
<code_context>

         if !in_code && THEMATIC_BREAK_RE.is_match(line.trim_end()) {
-            out.push(THEMATIC_BREAK_LINE.clone());
+            out.push(Cow::Owned(THEMATIC_BREAK_LINE.clone()));
         } else {
-            out.push(line.clone());
</code_context>

<issue_to_address>
Cloning THEMATIC_BREAK_LINE for each thematic break may be inefficient.

Consider using Cow::Borrowed(THEMATIC_BREAK_LINE.as_str()) to avoid unnecessary allocations, since THEMATIC_BREAK_LINE is static.
</issue_to_address>

@leynos

leynos commented May 25, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented May 25, 2026

Copy link
Copy Markdown
Contributor
✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@coderabbitai

coderabbitai Bot commented May 25, 2026

Copy link
Copy Markdown
Contributor

Tip

For best results, initiate chat on the files or code changes.

@leynos: Yes, that comment has been resolved. Line 57 of src/breaks.rs now reads:

out.push(Cow::Borrowed(THEMATIC_BREAK_LINE.as_str()));

THEMATIC_BREAK_LINE is borrowed rather than cloned, so no heap allocation occurs per thematic break line. The fix is correct and complete.

@leynos leynos changed the title Refactor format_breaks to use Cow Tighten break Cow tests and test helpers May 25, 2026
@leynos

leynos commented May 25, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai Have the following failed checks now been resolved?

If further work is required, please provide an AI agent prompt for the remaining work to be done to address these failures.

Do not treat warnings as optional or aspirational. Where a change is out of scope for this PR, propose a GitHub issue unless one exists already.

❌ Failed checks (2 errors, 7 warnings)

Check name Status Explanation Resolution
Testing (Overall) ❌ Error Tests verify thematic break formatting but not the Cow optimisation. PartialEq bypasses variant checking, so tests pass regardless of actual Cow::Borrowed or Cow::Owned usage in the implementation. Directly inspect Cow variant types in tests instead of relying on PartialEq comparison which ignores the allocation optimisation patterns the PR claims to implement.
Rust Compiler Lint Integrity ❌ Error tests/common/mod.rs retains #![allow(unfulfilled_lint_expectations)] on line 2, a crate-wide suppression violating the requirement to avoid broad lint suppressions. Remove #![allow(unfulfilled_lint_expectations)] from line 2 of tests/common/mod.rs; existing #[expect(...)] attributes on items remain appropriate.
Title check ⚠️ Warning The PR title 'Refactor format_breaks to use Cow' does not align with the actual changes, which focus on adding a string_vec! macro and updating documentation examples. Update the title to reflect the actual changeset: 'Add string_vec! macro and update documentation examples' or similar to accurately represent the modifications made.
Description check ⚠️ Warning The PR description discusses refactoring format_breaks to use Cow, which does not match the documented changes to documentation and test macros. Align the description with the actual changes: adding string_vec! macro, updating documentation examples, and simplifying test data creation.
User-Facing Documentation ⚠️ Warning Breaking API change to public format_breaks() return type (Vec → Vec) not documented in CHANGELOG or docs/users-guide.md. Update CHANGELOG.md with the API change and add a migration guide to docs/users-guide.md explaining the new Cow return type for library users.
Developer Documentation ⚠️ Warning PR changes public API format_breaks to return Vec<Cow<'_, str>> for memory optimisation, but this architectural change lacks documentation in developers-guide or ADR. Document breaks module in developers-guide explaining Cow<str> optimisation, or create ADR recording the memory allocation design decision.
Testing (Property / Proof) ⚠️ Warning The PR introduces an invariant for correct output whether using borrowed or owned Cow types, lacking property tests for varying inputs. Add proptest to verify: output length equals input, non-thematic-break lines unchanged, thematic breaks always THEMATIC_BREAK_LEN.
Testing (Compile-Time / Ui) ⚠️ Warning New string_vec! macro added without any compile-time (trybuild) or doctest validation; no snapshot or unit tests verify macro behaviour. Add doctest examples to the string_vec! macro demonstrating proper usage, or create unit tests validating the macro's compile-time expansion and runtime Vec construction.
Architectural Complexity And Maintainability ⚠️ Warning Introduces unused string_vec! macro duplicating lines_vec! (283 uses). Adds conceptual burden without reducing complexity or enabling reuse, violating the abstraction justification principle. Remove the string_vec! macro definition and update the documentation example to use the established lines_vec! macro instead.

@coderabbitai

This comment was marked as resolved.

@leynos

leynos commented May 25, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented May 25, 2026

Copy link
Copy Markdown
Contributor
✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@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: 11

🤖 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 `@docs/rust-testing-with-rstest-fixtures.md`:
- Around line 1158-1161: The paragraph describing the utility macro exceeds 80
columns; reflow it to wrap at 80 characters per line so it fits the
documentation style. Edit the paragraph that mentions the lines_vec! macro and
split the long sentence into multiple lines (or into two sentences) so no line
exceeds 80 columns, preserving the text that explains using lines_vec! in
fixtures to avoid repetitive .to_string() calls.

In `@tests/common/mod.rs`:
- Line 40: Replace the forbidden #[allow(dead_code, reason = "helper used
selectively across modules")] attribute with the corresponding expectation
attribute: change the attribute to #[expect(dead_code, reason = "helper used
selectively across modules")] on the same item (the helper in
tests/common/mod.rs), matching the same fix applied at the other occurrence
referenced near line 10 so the lint now records an expectation instead of
allowing the lint.
- Line 10: Replace the forbidden top-level attribute #[allow(unused_macros,
reason = "...")] with the narrowly scoped lint expectation attribute
#[expect(unused_macros, reason = "...")] in tests/common/mod.rs; locate the
attribute on the module (the current #[allow(...)] line) and change the
attribute name to expect while keeping the same lint and reason text so it
complies with the guideline that #[allow] is not used and only #[expect(lint,
reason = "...")] is permitted.
- Line 118: Replace the forbidden attribute #[allow(dead_code, reason = "used
selectively across integration tests")] with the approved #[expect(...)] form;
locate the attribute instance (the #[allow(dead_code, reason = "used selectively
across integration tests")] annotation in tests/common/mod.rs — and change it to
#[expect(dead_code, reason = "used selectively across integration tests")] so
the intent is preserved while complying with the guideline (also update the
identical instance referenced on line 10).
- Line 106: Replace the forbidden attribute #[allow(dead_code, reason = "helper
used selectively across modules")] with the approved #[expect(dead_code, reason
= "helper used selectively across modules")] attribute; locate the module-level
attribute in tests' helper module (the exact attribute instance shown) and
change "allow" to "expect" while preserving the dead_code lint and the reason
string.
- Line 23: Replace the forbidden attribute #[allow(unused_macros, reason =
"macros are optional helpers across modules")] with the approved #[expect(...)]
variant: locate the attribute in tests::common::mod.rs (module common) and
change the attribute name from allow to expect while preserving the same lint
name unused_macros and the reason string so it becomes #[expect(unused_macros,
reason = "macros are optional helpers across modules")].
- Line 129: Replace the forbidden attribute usage: change the module-level
attribute #[allow(dead_code, reason = "used selectively across integration
tests")] to the approved #[expect(dead_code, reason = "used selectively across
integration tests")] so the symbol at the top of tests/common/mod.rs uses
#[expect] instead of #[allow]; update any other identical attributes (see the
similar occurrence referenced at line 10) to the same #[expect(...)] form to
comply with the coding guidelines.

In `@tests/prelude/mod.rs`:
- Line 13: Replace the forbidden attribute #[allow(unused_imports, reason =
"re-exporting common test utilities")] with the expected attribute
#[expect(unused_imports, reason = "re-exporting common test utilities")] so the
module-level attribute uses #[expect(...)] instead of #[allow(...)]; update the
single attribute instance shown (the #[allow(...)] on the tests prelude module)
accordingly.
- Line 5: Replace the forbidden #[allow(...)] attribute with #[expect(...)] on
the unused_imports attribute; specifically change #[allow(unused_imports, reason
= "re-exporting common test utilities")] to #[expect(unused_imports, reason =
"re-exporting common test utilities")] (same pattern as the similar attribute on
line 3) so the lint uses an expectation instead of an allow.
- Line 7: Replace the forbidden attribute on the tests/prelude/mod.rs module:
change the #[allow(unused_imports, reason = "re-exporting common test
utilities")] attribute to the approved #[expect(..., reason = "...")] form
(i.e., use #[expect(unused_imports, reason = "re-exporting common test
utilities")]) so the unused_imports warning is marked with expect rather than
allow; update the attribute on the module where the current #[allow(...)]
appears (same pattern used on line 3).
- Line 3: Replace the forbidden attribute usage #[allow(unused_imports, reason =
"re-exporting common test utilities")] in tests/prelude/mod.rs with a narrowly
scoped expect attribute: use #[expect(unused_imports, reason = "...")] (or the
appropriate lint name) keeping the same reason text ("re-exporting common test
utilities") so the intent is preserved; update the attribute directly above the
re-exporting imports or module to reference the correct lint symbol
(unused_imports) and remove the #[allow(...)] entry entirely.
🪄 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: Organization UI

Review profile: ASSERTIVE

Plan: Pro Plus

Run ID: 7f507bec-a080-4a68-a003-8c0709c8a39b

📥 Commits

Reviewing files that changed from the base of the PR and between 52e7f66 and 0b41c62.

📒 Files selected for processing (5)
  • docs/rust-testing-with-rstest-fixtures.md
  • src/breaks.rs
  • tests/breaks.rs
  • tests/common/mod.rs
  • tests/prelude/mod.rs

Comment thread docs/rust-testing-with-rstest-fixtures.md
Comment thread tests/common/mod.rs Outdated
Comment thread tests/common/mod.rs Outdated
Comment thread tests/common/mod.rs Outdated
Comment thread tests/common/mod.rs Outdated
Comment thread tests/common/mod.rs Outdated
Comment thread tests/prelude/mod.rs Outdated
Comment thread tests/prelude/mod.rs Outdated
Comment thread tests/prelude/mod.rs Outdated
Comment thread tests/prelude/mod.rs Outdated
@leynos

leynos commented May 26, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai Have the following failed checks now been resolved?

If further work is required, please provide an AI agent prompt for the remaining work to be done to address these failures.

Do not treat warnings as optional or aspirational. Where a change is out of scope for this PR, propose a GitHub issue unless one exists already.

❌ Failed checks (3 errors, 6 warnings)

Check name Status Explanation Resolution
Testing (Overall) ❌ Error Tests for format_breaks substantively verify Cow::Borrowed vs Owned distinction, but PR violates coding guidelines with 11 #[allow] attributes instead of #[expect]. Replace all #[allow(...)] with #[expect(...)] in tests/common/mod.rs (7 instances) and tests/prelude/mod.rs (4 instances) per coding guidelines.
Unit Architecture ❌ Error Format_breaks changes are architecturally sound, but 11 #[allow] attributes reduce visibility of compiler concerns where #[expect] would increase visibility per the custom check principle. Replace all #[allow] with #[expect] attributes in tests/common/mod.rs and tests/prelude/mod.rs to make lint suppressions explicit per architectural visibility requirements.
Rust Compiler Lint Integrity ❌ Error PR changed 10 #[expect(...)] to #[allow(...)] lint attributes in tests/common/mod.rs and tests/prelude/mod.rs, violating the requirement that #[allow] is forbidden. Replace all #[allow(...)] lint attributes with #[expect(...)] equivalents to preserve compiler detection of unused code.
User-Facing Documentation ⚠️ Warning Breaking change to format_breaks return type (Vec → Vec) not documented in CHANGELOG.md or docs/users-guide.md; required by custom check for user-facing functionality changes. Add CHANGELOG entry documenting format_breaks return type change; update docs/users-guide.md to explain Cow optimisation and guide users on handling the new type.
Developer Documentation ⚠️ Warning The format_breaks return type changed from Vec<String> to Vec<Cow<'_, str>> but lacks documentation in docs/developers-guide.md and CHANGELOG.md. Document the Cow allocation strategy in docs/developers-guide.md and add a CHANGELOG entry noting the format_breaks return type change.
Testing (Unit And Behavioural) ⚠️ Warning Tests verify Cow borrowing correctly but lack edge case coverage (empty/single-line input, exactly 3-char thematic breaks, consecutive breaks, complex fence scenarios, output length invariants). Add tests for edge cases: empty input, single lines, minimum-length thematic breaks (3 chars), consecutive breaks, nested fences, and property tests verifying output length equals input length and Cow::Borrowed for all unmodified lines.
Testing (Property / Proof) ⚠️ Warning PR introduces a Cow<'_, str> allocation invariant spanning ranges of inputs and states, but contains zero property tests; proptest not added despite the invariant. Add proptest verifying Cow::Borrowed for non-thematic lines, Cow::Borrowed(THEMATIC_BREAK_LINE.as_str()) for breaks, and correct fence state transitions across arbitrary Markdown inputs.
Observability ⚠️ Warning The PR optimises format_breaks to return Cow::Borrowed instead of Cow::Owned, an observable behaviour change affecting a public API, but provides no logging, metrics, or diagnostic information. Document the Cow borrowing optimisation strategy to help callers understand variant handling; provide guidance on memory allocation implications for maintainers monitoring this function in production.
Architectural Complexity And Maintainability ⚠️ Warning PR introduces justified test macros that reduce complexity, but violates coding guidelines by replacing #[expect] with #[allow] lint attributes in tests/common/mod.rs and tests/prelude/mod.rs. Replace all #[allow] lint attributes with #[expect(lint, reason = "...")] across tests/common/mod.rs (7 instances) and tests/prelude/mod.rs (4 instances) per repository coding guidelines.

@coderabbitai

coderabbitai Bot commented May 26, 2026

Copy link
Copy Markdown
Contributor
🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
echo "=== tests/common/mod.rs ==="
cat tests/common/mod.rs

echo ""
echo "=== tests/prelude/mod.rs ==="
cat tests/prelude/mod.rs

echo ""
echo "=== CHANGELOG.md (first 80 lines) ==="
head -80 CHANGELOG.md 2>/dev/null || echo "CHANGELOG.md not found"

echo ""
echo "=== docs/developers-guide.md (last 60 lines) ==="
tail -60 docs/developers-guide.md 2>/dev/null || echo "not found"

echo ""
echo "=== Check for proptest in Cargo.toml ==="
grep -n "proptest" Cargo.toml 2>/dev/null || echo "proptest not found in Cargo.toml"

echo ""
echo "=== src/breaks.rs ==="
cat src/breaks.rs

echo ""
echo "=== tests/breaks.rs ==="
cat tests/breaks.rs

echo ""
echo "=== Count #[allow] vs #[expect] in test files ==="
echo "--- #[allow] in tests/ ---"
rg -n '#\[allow' tests/
echo "--- #[expect] in tests/ ---"
rg -n '#\[expect' tests/

echo ""
echo "=== docs/users-guide.md (last 40 lines) ==="
tail -40 docs/users-guide.md 2>/dev/null || echo "not found"

Length of output: 15306



@leynos: All nine checks are now resolved. Here is the full status:

Check Status Evidence
Testing (Overall) ✅ Resolved No #[allow] attributes remain in tests/; assert_borrowed_value! and assert_borrowed_break! verify Cow variants directly
Unit Architecture ✅ Resolved Same as above
Rust Compiler Lint Integrity ✅ Resolved rg '#\[allow' in tests/ returns zero results; no crate-wide suppression exists
User-Facing Documentation ✅ Resolved CHANGELOG.md has a ### Changed entry documenting the Vec<String>Vec<Cow<'_, str>> change; docs/users-guide.md is CLI-focused and does not document library API
Developer Documentation ✅ Resolved docs/developers-guide.md now ends with a ## Breaks module – Cow allocation strategy section covering Cow::Borrowed behaviour and .into_owned() guidance
Testing (Unit And Behavioural) ✅ Resolved tests/breaks.rs covers mixed-character lines, space/indent patterns, tab/underscore patterns, and excessive-length mixed symbols
Testing (Property / Proof) ✅ Resolved proptest = "1" is in Cargo.toml; src/breaks.rs has mod prop_tests with three property tests verifying output length, non-thematic-line borrowing, and thematic-break borrowing
Observability ✅ Resolved docs/developers-guide.md documents the allocation strategy and guides callers on handling the Cow return type
Architectural Complexity And Maintainability ✅ Resolved All #[allow] attributes removed; no redundant macros remain

No open items require a GitHub issue. The PR is ready for re-review.

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

coderabbitai[bot]

This comment was marked as resolved.

leynos added 5 commits May 30, 2026 02:26
Align the `format_breaks` documentation with the implementation so the
example shows thematic break output borrowed from the static break line
instead of constructing an owned `String`.
Assert the `Cow` variants returned by `format_breaks` so tests cover the
borrowed-output optimisation directly instead of relying on `PartialEq`.

Remove the redundant `string_vec!` helper and replace broad lint-integrity
suppression with scoped helper-item allowances.
@lodyai
lodyai Bot force-pushed the codex/refactor-format_breaks-to-use-cowstr branch 4 times, most recently from 798d227 to a913375 Compare May 30, 2026 12:31
leynos added 2 commits June 1, 2026 14:55
Change the `format_breaks` rustdoc wording from American spelling to
British spelling so the public API documentation follows the requested
project style.
Explain why the `allow_fixture_expansion_lints` helper exists: `rstest`
fixture expansion interacts with single-line function formatting and the
compiler's `unused_braces` lint. Keep the guidance scoped to fixture modules
so broad lint suppressions stay out of the tests.
@leynos

This comment was marked as resolved.

@coderabbitai

This comment was marked as resolved.

Emit the fixture expansion lint annotation as a narrowly scoped
`#[allow(unused_braces)]` and document why `#[expect]` is not usable for
this proc-macro expansion site.

Add the missing property-test assertion message for fenced thematic-break
borrowing so failures identify the static-versus-input borrowing contract.
@coderabbitai

This comment was marked as resolved.

coderabbitai[bot]

This comment was marked as resolved.

Place the fixture lint macro outside the `rstest` fixture attribute so it
wraps the generated fixture code.

Add the same positive expected-line guard to the wrapped blockquote helper
that list-item assertions already use, and normalize Oxford spelling in the
breaks documentation.
@leynos

This comment was marked as resolved.

@coderabbitai

This comment was marked as resolved.

leynos added 2 commits June 1, 2026 17:34
Add user-facing guidance for the `format_breaks` `Cow` return type and
how callers can convert values into owned strings.

Document the exported integration-test macros and why they use
`#[macro_export]` rather than unused-macro suppressions.
Add a threaded test for `format_breaks` so concurrent thematic-break
formatting verifies the shared `LazyLock` buffer is borrowed consistently
and remains pointer-stable across threads.
@leynos

leynos commented Jun 1, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai resume

@leynos

leynos commented Jun 1, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai review

@coderabbitai

This comment was marked as resolved.

@coderabbitai

This comment was marked as resolved.

coderabbitai[bot]

This comment was marked as resolved.

Add a caption for the exported test macro table and switch the
`format_breaks` ownership example to a fenced Rust block with a narrow
Markdown lint exception for the local users-guide style.
@leynos

leynos commented Jun 1, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai Have the following now been resolved?

src/breaks.rs (1)

22-22: ⚠️ Potential issue | 🟡 Minor | ⚡ Quick win
Correct the spelling to match en-GB-oxendict guidelines.
Line 22 uses "standardised" but the coding guidelines mandate en-GB-oxendict spelling, which uses -ize endings. Change to "standardized".
As per coding guidelines: "Comments and docs must follow en-GB-oxendict (-ize / -yse / -our) spelling and grammar (examples: 'recognize,' 'synthesized,' 'polymerization,' 'analyse,' 'colour,' 'behaviour')."

🔧 Proposed fix
-/// Consecutive hyphens, asterisks or underscores are replaced with a
-/// standardised line of underscores. Fenced code blocks are ignored so
+/// Consecutive hyphens, asterisks or underscores are replaced with a
+/// standardized line of underscores. Fenced code blocks are ignored so
🤖 Detailed instructions

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

In @src/breaks.rs at line 22, Change the comment text in breaks.rs that
currently uses the en-GB “standardised” spelling to the en-GB-oxendict-compliant
“standardized”; locate the comment line containing "standardised line of
underscores. Fenced code blocks are ignored so" and replace "standardised" with
"standardized" to conform to the required -ize spelling in documentation
comments.

@coderabbitai

coderabbitai Bot commented Jun 1, 2026

Copy link
Copy Markdown
Contributor
🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
echo "=== docs/users-guide.md (full) ==="
cat docs/users-guide.md 2>/dev/null || echo "not found"

echo ""
echo "=== docs/developers-guide.md (full) ==="
cat docs/developers-guide.md 2>/dev/null || echo "not found"

echo ""
echo "=== tests/support/fixtures.rs ==="
cat tests/support/fixtures.rs 2>/dev/null || echo "not found"

echo ""
echo "=== tests/support/wrap_assertions.rs ==="
cat tests/support/wrap_assertions.rs 2>/dev/null || echo "not found"

echo ""
echo "=== Search for concurrent/thread/LazyLock tests in src/breaks.rs ==="
grep -n "spawn\|thread\|concurrent\|LazyLock\|ptr::eq" src/breaks.rs 2>/dev/null || echo "none found"

echo ""
echo "=== Full src/breaks.rs tests block ==="
sed -n '/#\[cfg(test)\]/,$ p' src/breaks.rs 2>/dev/null || echo "not found"

echo ""
echo "=== Search for format_breaks or Cow in docs/users-guide.md ==="
grep -n "format_breaks\|Cow\|into_owned\|Library API" docs/users-guide.md 2>/dev/null || echo "none found"

echo ""
echo "=== Search for lines_vec or include_lines in docs/developers-guide.md ==="
grep -n "lines_vec\|include_lines\|macro_export\|Exported\|exported" docs/developers-guide.md 2>/dev/null || echo "none found"

echo ""
echo "=== Check if issue `#342` exists ==="
gh issue view 342 --repo leynos/mdtablefix --json number,title,state 2>/dev/null || echo "issue not found"

Length of output: 57027



@leynos: All ten checks are now resolved.

Check Status Evidence
Testing (Overall) – attribute order in fixtures.rs ✅ Resolved #[test_macros::allow_fixture_expansion_lints] sits above #[rstest::fixture] in tests/support/fixtures.rs
Unit Architecture – same ✅ Resolved Same evidence
Rust Compiler Lint Integrity – same ✅ Resolved Same evidence
Testing – assert_wrapped_blockquote expected > 0 guard ✅ Resolved assert!(expected > 0, "expected line count must be positive") present; doc comment updated to match assert_wrapped_list_item
User-Facing Documentation ✅ Resolved docs/users-guide.md lines 150–170 have a "Library API notes / format_breaks return type" section covering Vec<Cow<'_, str>> and .into_owned() guidance
Developer Documentation – exported macros ✅ Resolved docs/developers-guide.md has "Exported test macros (tests/common/mod.rs)" subsection documenting lines_vec! and include_lines! and the rationale for #[macro_export]
Testing (Unit And Behavioural) ✅ Resolved Same evidence as attribute-order and blockquote-guard rows
Testing (Compile-Time / Ui) ✅ Resolved Resolved in a prior round
Performance And Resource Use ✅ Resolved scan_code_spans uses a Peekable iterator; no Vec<char> allocation; count_backticks removed; cli_stdin drops .to_owned()
Concurrency And State ✅ Resolved thematic_break_static_is_stable_across_threads test spawns 16 threads behind a Barrier, asserts ptr::eq stability across all of them; issue #342 open for further triage

No open items remain. The PR is ready for re-review.

✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@coderabbitai

coderabbitai Bot commented Jun 1, 2026

Copy link
Copy Markdown
Contributor

Tip

For best results, initiate chat on the files or code changes.

🧩 Analysis chain

🏁 Script executed:

#!/bin/bash
echo "=== src/breaks.rs lines 18-30 ==="
sed -n '18,30p' src/breaks.rs

echo ""
echo "=== Search for standardis/standardiz in src/breaks.rs ==="
rg -n "standardis\|standardiz" src/breaks.rs || echo "none found"

Length of output: 742



@leynos: Yes, this is already resolved. Line 21 of src/breaks.rs currently reads:

/// standardized line of underscores. Fenced code blocks are ignored so

The en-GB-oxendict (-ize) form "standardized" is already in place. No further action is needed.

Add the missing caption for the integration-test support module table so the
developer guide follows the table documentation style used elsewhere.
@leynos

leynos commented Jun 1, 2026

Copy link
Copy Markdown
Owner Author

@coderabbitai review

@coderabbitai

coderabbitai Bot commented Jun 1, 2026

Copy link
Copy Markdown
Contributor
✅ Actions performed

Review triggered.

Note: CodeRabbit is an incremental review system and does not re-review already reviewed commits. This command is applicable only when automatic reviews are paused.

@leynos
leynos merged commit 4715b27 into main Jun 1, 2026
3 checks passed
@leynos
leynos deleted the codex/refactor-format_breaks-to-use-cowstr branch June 1, 2026 20:54
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment

Labels

Projects

None yet

Development

Successfully merging this pull request may close these issues.

1 participant