Resolved multiple Iru users sharing an email#2
Merged
Conversation
Renamed FindUserByEmail to FindUsersByEmail and dropped the hardcoded limit=1. The walk now paginates via WalkCursor so every user record sharing the same email is returned. Both production callers were updated to compile against the new signature; the cmd layer still uses the first match for now (multi-match disambiguation lands in a follow-up task) with an explicit empty-slice guard.
Extracted the device + detection bucketing into a helper that takes an already-resolved iru.User. resolveBundleForUser keeps its existing behaviour by calling the new helper. The user-show disambiguation work depends on being able to build a bundle from a chosen user without re-running the identifier lookup.
Reworded the doc comment so it does not name resolveSelectedUser before that function exists. The intent is unchanged: once the multi-user disambiguation work lands, user show will call buildBundleForUser directly with a pre-selected user.
Introduced resolveSelectedUser plus the userStatusLabel, userOneLine, and promptForUser helpers. On TTY the user is shown a numbered menu and picks one of the matches; on non-TTY a structured error names every match and prints a re-run hint. The new helper is not wired into runUserShow yet — that lands in the next task.
Added a direct unit test for the zero-match case so the path is not only exercised indirectly through resolveBundleForUser.
userShowOpts gained PromptReader and stdinIsTTY hooks for tests. On a real TTY a numbered menu is shown; on non-TTY the command errors with a re-run hint listing every match. A clean q / EOF prints "aborted: no user shown" and exits 0.
The bulk recipient loop now resolves each input email to every matching Iru user and processes them independently. When one input maps to more than one user, stderr lines gain a user=<id> segment so each fanout is auditable; single-match inputs are unchanged. The temporary resolveBundleForUser bridge was removed; the test fake's ListDevices now honours UserID so per-user bundles isolate cleanly.
Added a doc comment on the iruClient method declaring that an empty result must come back as ErrNotFound, never (nil, nil), and added a defensive guard in the bulk send loop so a future implementation that violates the contract still produces a user-not-found log line rather than silently dropping input.
Added two regression tests confirming that two Iru users sharing an email both appear in the overview roster with their own ranks, and that overview --per-user --send-email fans out to each of them independently. No production code change.
The shared on-disk detection cache survives across cmd tests in one run; a sibling test populates it with unrelated fixtures. This test passes noCache=true so it sees its own fakeClient data and not the stale cache.
Added one short paragraph each to the user show, users send-email, and overview sections describing how duplicate emails are handled, including the new prompt / non-TTY re-run hint, the user=<id> stderr segment for bulk fanouts, and the fact that the overview roster is keyed by user ID.
Dropped the internal endpoint path from the user-facing description and reworded the non-TTY error description so it reflects the single-line message that actually prints.
The prompt previously said "to N users" using the input-row count, but one input email can now expand to multiple Iru-user sends. Reworded to "to N input address(es)" so operator consent matches what is actually being counted.
|
Codecov Report❌ Patch coverage is
📢 Thoughts on this report? Let us know! |
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.
Summary
internal/iru.FindUserByEmailwas renamed toFindUsersByEmail, dropped the hardcodedlimit=1, and now paginates viaWalkCursorso every user record sharing an email is returned.ErrNotFoundis returned only on zero matches.user show <email>now disambiguates multi-match emails: a numbered prompt on a TTY, or a single-line error with every matching user ID and a re-run hint on a pipe / CI. The new helpers (resolveSelectedUser,userStatusLabel,userOneLine,promptForUser,buildBundleForUser) live incmd/user.go; tests cover single match, multi-match TTY pick, invalid-then-valid, three-strike exhaustion, abort, non-TTY error, andErrNotFound.users send-emailexpands each input email into N users via the same lookup and processes each user independently. Per-row stderr lines gain auser=<id>segment when an input maps to more than one Iru user; single-match inputs are unchanged. Summary counters reflect user-level outcomes, not input rows. The consent prompt now reads "to N input address(es)" so it doesn't overstate the granularity.overviewandoverview --per-user --send-emailneed no production change because the roster is already keyed by user ID; two regression tests incmd/overview_test.gopin that behaviour.Test plan
make pre-ciis green (9/9 checks, coverage 81.1%, govulncheck clean).go test ./...is green across all 9 packages.jellyfish user show aravinth@flipgroup.com.aunow lists both matching users instead of silently picking the first.