Skip to content

modern Rust API adoption gated behind MSRV bump (1.88 -> 1.9x) #9

Open

Description

@bug-ops

Description

Per the new mandatory per-cycle "Modern Rust API / MSRV audit" check in .claude/rules/continuous-improvement.md, this cycle scanned crates/rmcp/src and crates/rmcp-macros/src against the rust-agents:rust-modern-apis trigger table (stable APIs added 1.89-1.97). Current workspace MSRV is 1.88 (Cargo.toml rust-version).

Findings

  • Duration::from_secs(60) appears as a literal one-minute duration in 9 call sites (task_manager.rs, transport/streamable_http_server/session/local.rs, model/request_state.rs). Duration::from_mins(1) (stable 1.91) would read marginally clearer but the win is purely cosmetic for a self-evidently-60-second constant.
  • assert!(matches!(...)) appears 90 times, all inside #[cfg(test)] modules or crates/rmcp/tests/* integration tests (23 files) — assert_matches! (stable 1.96) would give better failure output (prints the actual value), but per the audit skill's own guidance this is test-only styling, not a correctness issue.
  • No occurrences of the other trigger patterns (with_extension add-suffix misuse, try_into().unwrap() for fixed arrays, compare_exchange CAS loops, cfg_if crate usage, fs2/fd-lock external locking, bit-manipulation via leading_zeros/wrapping_neg, unbounded_channel, manual file_stem composition).

Assessment

None of the above rises to a correctness or safety liability — all are readability-only. Bumping MSRV to unlock them (nearest useful target: 1.91 for Duration::from_mins, 1.96 for assert_matches!) is itself a breaking change under this project's versioning discipline (cargo-semver-checks/cargo public-api diff gates, downstream toolchain compatibility for every consumer pinned between 1.88 and the target). That cost is not justified by a handful of cosmetic call sites, most of which are test-only.

Recommendation: do not bump MSRV for this alone. Revisit if/when an MSRV bump is already warranted for an unrelated reason (e.g. a dependency requiring a newer toolchain) — at that point, adopt Duration::from_mins/from_hours and assert_matches! opportunistically as part of the same bump rather than as a standalone change.

Environment

  • Version: 3.1.2 (02c62ae)
  • MSRV: 1.88 (workspace Cargo.toml)

Upstream

None found — searched modelcontextprotocol/rust-sdk issues/PRs (state: all) for "MSRV modern API" / "assert_matches" / "Duration::from_mins", no matches.

Logs / Evidence

Grep commands used: Duration::from_secs(60, assert!(matches!(, with_extension(, try_into().unwrap(), compare_exchange, cfg_if, fs2|fd-lock, leading_zeros|wrapping_neg, file_stem, unbounded_channel across crates/rmcp/src, crates/rmcp/tests, crates/rmcp-macros/src.

Activity

  1. added
    enhancementNew feature or request
    architectureArchitecture and structural design
    P4Nice-to-have: research ideas, future enhancements
    on Aug 8, 2026
  2. bug-ops commented on Aug 8, 2026

    @bug-ops
    OwnerAuthor

    Re-verified for cycle ci-005 (main still at 02c62ae, no change since this issue was filed).

    Extended the sweep to the full current rust-agents:rust-modern-apis trigger table (which has grown since this issue's original grep list) — checked extract_if/retain, Result::flatten, slice::as_array/array_windows, Ipv4Addr::/Ipv6Addr::new, LazyLock/LazyCell/OnceLock init-check patterns, pop_front_if/pop_back_if, with_extension, compare_exchange, cfg_if, unbounded_channel. No new candidates found:

    • 8 .retain() call sites, none need visibility into removed items (not extract_if candidates)
    • The one Result<Result<...>> is a channel-recv type alias (oneshot::error::RecvError wrapping a Result), not a manual flatten
    • OnceLock/LazyLock usages already use .get()/idiomatic init patterns
    • No IP address construction, no CAS loops, no manual UTF-8 boundary math, no unbounded channels

    Original assessment (do not bump MSRV for cosmetic wins alone) still stands.

  3. github-actions commented on Oct 8, 2026

    @github-actions

    This issue has had no activity for 60 days and is now marked as stale. It will be closed in 14 days if there is no further activity. Add the keep label to keep it open.

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

    P4Nice-to-have: research ideas, future enhancementsStalearchitectureArchitecture and structural designenhancementNew feature or request

    Projects

    No projects

      Milestone

      No milestone

      Relationships

      None yet

      Development

      No branches or pull requests

      Issue actions