Repository navigation
feat(trade): agent UX — lock-free discover, serve-handled takes, unresponsive warning, readable status, fee dry-run (stacked on #1119) - #1125
Merged
Conversation
…sponsive warning, readable status, fee dry-run - discover: ephemeral relay key, no owner.lock/journal/home creation; per-lot expected fees (unknown when a mint is unreachable) - serve binds <home>/serve.sock (0600, same-uid peers, one bounded request per connection); list/take/cancel hand off with the client's exact bounds and run inside serve's loop (single writer) - counterparty_unresponsive display state after 180 s (take, serve log, status); display only - status prints a human summary; status --json unchanged (golden test) - --dry-run on list/take: both legs' fees, gross and max debit, zero side effects - tests/ux.rs safety tests
The lot id hashes second-granular terms; two identical list requests handed to serve back-to-back produced the same id and the second journal row overwrote the first, orphaning its reservation. list now waits for a fresh id (or refuses). Found by the concurrent clients/serve race test, which now prints client and serve output on failure.
…tRefusal, persist-before-report, receive status; keep both docs sets)
…ILL under 10 kB
|
The latest updates on your projects. Learn more about Vercel for GitHub.
|
maxie-agent
changed the base branch from
feat/credit-trade-receive
to
feat/credit-trade
October 11, 2026 01:13
…dit-trade-ux # Conflicts: # crates/maxplayer-trade/skills/maxplayer-trade/SKILL.md # crates/maxplayer-trade/skills/maxplayer-trade/references/commands.md # crates/maxplayer-trade/src/coordinator.rs # crates/maxplayer-trade/src/lib.rs # crates/maxplayer-trade/src/main.rs
maxie-agent
marked this pull request as ready for review
October 11, 2026 02:52
This branch was successfully deployed
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.
Stacked on #1119 (base
feat/credit-trade-receive). Agent-UX changes for the standalonemaxplayer-tradeCLI, scope approved by Bob. No protocol, lock-duration, deadline or split-solver changes; nosend.Feedback each item answers
discoveris lock-free and read-only: ephemeral relay key, never opens the journal, never takesowner.lock, never creates a home.serveowns the home,list/take/cancelhand the request to serve over<home>/serve.sock; serve runs it with exactly the client's bounds and stays the single writer. Same stdout, stderr and exit codes as a direct run.counterparty_unresponsivedisplay state after 180 s without a counterparty message, shown intake, the serve log andstatus, with elapsed time and when the refund becomes available. Display only.statusprints a human summary (unresolved first, exit-code legend).status --jsongives byte-for-byte today's output (golden test).--dry-runonlist/takeshows both legs' fees, gross amounts, max total debit and whether the real command would refuse, with zero side effects.discoveradds per-lotexpected_fees(unknownwhen a mint is unreachable; never blocks).Design
src/serve.rs: a Unix socket created while serve holdsowner.lock, so any existing socket file is stale and gets replaced (a non-socket is refused). Mode 0600 inside the 0700 home; SO_PEERCRED same-uid check on both sides. One request per connection; requests capped at 16 KiB, reply lines at 64 KiB; 10 s I/O timeouts; at most 8 connections;deny_unknown_fieldsand no serde defaults for bounds, so serve can't fill in a missing or looser bound. The request carries the client's relay set and serve refuses a mismatch. Jobs go intocoordinator::run_withand execute in serve's own select loop between inbox messages and recovery ticks, through the same coordinator functions (journal before effect), so a request is either journaled or rejected and never half-applied. A client that disconnects never cancels a request; serve keeps driving the take. If serve goes silent the client exits 3 and points tostatus.main.rs: try the socket → try the lock → retry the socket for 5 s (covers serve still binding, or a short-lived writer such asrecover) → "home is already in use". It never runs as a second writer.src/observe.rs: read-only SQLite views (SQLITE_OPEN_READ_ONLY; nothing is created). Unresponsive state comes from the swap row'supdated_timeand role/state; refund time mirrors the coordinator gates without deciding anything. Lab-onlyTRADE_LAB_UNRESPONSIVE_SECONDSexists for tests.src/dryrun.rs: read-only keysets, plus a read-only wallet proof selection that mirrorsmint::plan.src/report.rs: the humanstatus.0194bb5): the lot id hashes second-granular terms, so two identicallists in the same second (easy once serve queues them back to back) shared an id, and the second journal row overwrote the first and orphaned its reservation.listnow waits for a fresh id or refuses. Two identical CLI lists in the same second could hit this before too, but the home lock made it unlikely.Test map (
tests/ux.rs, plus unit tests in observe/serve/dryrun)concurrent_clients_and_serve_never_make_two_writers(lab writer-tenure trace, success count = journaled listings, no input reserved twice);live_serve_owns_every_writetake_via_serve_enforces_client_bounds_exactly_and_settles; unitrequest_rejects_unknown_fields_and_keeps_boundsdry_run_has_zero_side_effects_and_matches_real_plan,dry_run_refusals_and_unsolvable_amounts_are_reporteddiscover_is_lock_free_and_never_touches_the_journal,discover_marks_unreachable_mint_fees_unknown_without_blockingstatus --jsongoldenstatus_json_matches_golden_and_summary_is_readable_and_secret_freestale_socket_and_bounded_protocol, unitbounded_linescounterparty_unresponsive_warning_is_display_only, observe unit testsdisconnected_client_leaves_take_with_serveVerification (local, head before this PR's merge commit fast-forward:
81e6ea6)cargo fmt --check; clippy default + lab with-D warningsand the CI allow list; all--locked.TRADE_LAB_SECONDS=1): 182 passed (lib 34, cli 5, e2e 11, money 17, pinned 1, receive 23, relays 7, review_regressions 46, round5 26, round7 1, ux 11).M1 discover takes the lock path · M2 serve take uses default
max_fees· M3 serve loosensmax_give+1 · M4 take--dry-runfalls through to the real take · M8 list--dry-runfalls through · M5status --jsongains a field · M7 socket 0666 · M6 owner-lock failure ignored · M9 lot-id collision guard removed.Merge of #1119
Merged
origin/feat/credit-trade-receiveat25cce15(typedMintRefusal, persist-before-report, receive status summary). The SKILL.md conflict was resolved so both sets of changes survive; it is 9,996 B, under the 10,000 B test limit. The golden test and #1119's receive status assertion now usestatus --json.Unverified
/proc/self/fd/N; the SO_PEERCRED behavior is Linux-specific.