Repository navigation
test: cover project users, organization users and teams - #237
pjcdawkins merged 11 commits into
Conversation
There was a problem hiding this comment.
Note
Reviewed — No blocking findings · 🔵 2 minor points
🔍 Full review · 10 files reviewed
🔵 Minor points
pkg/mockapi/teams.go:358—handleAddTeamProjectsvalidates and appends inside the same loop. Take a body like[{"project_id":"betaprojectid"},{"project_id":"unknown"}]: the first item is appended toh.teamProjects[teamID]before the second fails, and the handler then returns 400. The request is reported as failed, but the team now has access tobetaprojectid. A laterteam:projectscall, or an assertion that a failed add changed nothing, sees that partial state. To fix it, validate every item before appending any.pkg/mockapi/user_access.go:306—handlePatchOrgMemberwritesh.orgMembers[orgID][i] = &patchedstraight into the backing array. That array is the slice the test passed toSetOrgMembers, so a PATCH changes the caller's slice.handlePatchProjectUserAccess(line 178) does the same with theSetUserGrantsslice. The delete handlers in this file callslices.Clonefirst to avoid exactly this aliasing, so the two patch handlers break the convention and leak mutations into the test's own data.
Verification
handleDeleteTeamremoves the team's members and project access too, so/projects/{id}/team-accessnever lists a deleted team.lowercaseAlphanumericIDand the/ref/usershandler, which derives emails as<id>@example.com, exist in pkg/mockapi, so the expecteduser-id-2@example.comstrings in the tests match what the mock serves.- The project and org invitation handlers return 409 only when
forceis false, so the repeateduser:add(confirmed, then forced) records a second invitation, asTestUserAddasserts. - All new handlers lock the embedded store: RLock for reads and Lock for writes, including
initTeams, which documents that its caller holds the lock.
The change is test-only: new integration tests in integration-tests/ (org_user_test.go, team_test.go, user_access_test.go and the extended user_get_test.go) run against new mock API handlers. Nothing tests the mock handlers themselves beyond those integration tests, which run through the repository's make test-go target.
Review details
- Commit: e8a740d
- Model: claude-opus-5-5
Review 1 of 10 for this pull request · View the full run
Add project user-access updates and deletion, project and organization invitations, organization members, environment types, and teams with their members and project access. Project owners are now served. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Cover invitations (including a repeated one), role merging and changes, the project owner guards, deletion with and without confirmation, and user:get at the environment level, for an unknown user, and with the deprecated --role option. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Cover org:user:list and org:user:get, inviting a user, adding an existing user, permission changes (including "already set" and the owner guard), and deletion with and without confirmation. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Cover team:create (roles, --output-id, label uniqueness and conflicts), team:get, team:list (in an organization and on a project), team:update, team:delete, team:project:add/delete/list and team:user:add/delete/list. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Validate all projects before adding any to a team, and copy the user grants and organization members slices before patching them, so that tests' own slices are not modified. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
81a9aca to
218b38b
Compare
There was a problem hiding this comment.
Note
Reviewed — No blocking findings · 🔵 1 minor point
🔍 Full review · 10 files reviewed
🔵 Minor point
pkg/mockapi/teams.go:137—handleListTeamsalways sorts byLabeland only checks whethersortstarts with-. The field name is never read.TeamListCommandsendssort=<field>from its--sortoption, so a request liketeams --sort created_at(orupdated_at) still comes back in label order. A test that relies on any sort field other than label would get the wrong order with no warning.
Verification
handleAddTeamProjectsvalidates every project ID (it must exist and belong to the team's organization) before appending any access.handlePatchOrgMemberandhandlePatchProjectUserAccessboth clone the slice before replacing the element, so the slices tests pass toSetOrgMembers/SetUserGrantsare left unchanged.SetTeamsresets the member and project maps, andsetupTeamscallsSetTeamMembers/SetTeamProjectsafter it, so the seeded data survives.handleProjectUserAccessnow returns items built bynewProjectUserAccess, which embeds*ProjectUserGrant, so the JSON keeps the same fields and addsself/update/deletelinks.
The new integration tests (TestUserAdd/Update/Delete, TestOrgUser, TestTeam*, plus the extra TestUserGet cases) exercise the new mock API routes. They run under the repository's Go integration test job. Apart from what those tests call, nothing covers the mock handlers.
Review details
- Commit: 218b38b
- Model: claude-opus-5-5
Review 3 of 10 for this pull request · View the full run
Support sorting teams by label, created_at or updated_at (reversed with a "-" prefix), and reject other fields. Cover team:list --sort and --reverse. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
Align the new mocks with the API instead of the CLI's assumptions: - Teams: PATCH returns the team, labels need not be unique, the list sorts by created_at by default and has reference links, and members must belong to the organization. Adding a project the team already has is a conflict, and removing one it lacks succeeds. - Organization members: the owner cannot be updated or deleted (403), "admin" replaces other permissions, and the list has a count. - Project user access: permissions are validated, deleting a missing grant succeeds, items include the project title, and the list only references users. - Invitations: a project invitation's role is optional, environment type permissions are returned as "environments", forcing cancels the pending invitation, and organization invitations require permissions. - Environment types have attributes, and errors use the API's formats. The team:create test now expects a duplicate label to be accepted with --no-check-unique. Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…nization-users-and-teams
There was a problem hiding this comment.
Note
Reviewed — No blocking findings · 🔵 1 minor point
🔍 Full review · 10 files reviewed
🔵 Minor point
pkg/mockapi/teams.go:414—handleAddTeamProjectschecks each item only against the team's existingh.teamProjects[teamID]. It never checks items against each other in the same request body. A body like[{"project_id":"betaprojectid"},{"project_id":"betaprojectid"}]passes validation, and the second loop then appends twoTeamProjectAccessentries for the same project.team:projectsthen lists the project twice andproject_countcounts it twice. Calling the same endpoint twice gives 409 instead, so the duplicate is accepted only when it arrives in a single request.
Verification
handleAddTeamProjectsnow runs every validation check before it appends anything, so a failed request leavesteamProjectsunchanged.handlePatchProjectUserAccessandhandlePatchOrgMembercallslices.Cloneon the stored slice before they write to an index, so tests' slices are not mutated.handleListTeamshandles the sort fieldslabel,created_atandupdated_at, and returns 400 for any other field; TeamListCommand sendssort=labelby default, which the label-order assertions rely on.- The helpers the new files use (
timeCompare,lowercaseAlphanumericID,writeProblem,uniqueMap) exist in the base package.
The change is test-only: new integration tests in integration-tests/{org_user,team,user_access}_test.go and new cases in user_get_test.go, all run against the extended mock API. The repository's Go test target (make test-go) runs them. Nothing tests the mock handlers directly.
Review details
- Commit: 94dd22a
- Model: claude-opus-5-5
Review 6 of 10 for this pull request · View the full run
…quest Co-Authored-By: Claude Opus 5.5 <noreply@anthropic.com>
…t-users-organization-users-and-teams' into cli-210-integration-tests-project-users-organization-users-and-teams
Adds integration tests for the commands that grant or revoke access, and the mock API they need.
Mock API (
pkg/mockapi), in new files to keep edits to shared files small:user_access.go: project user-access GET/PATCH/DELETE (items now haveself/update/deletelinks), project and organization invitations (409 when already invited, unless forced), organization members, and project environment types.teams.go: teams, team members, team project access, and/projects/{id}/team-access.owner.None of these changes return activities: the CLI does not wait on them with centralized permissions, which the test config already enables.
Tests:
user:add,user:update,user:delete: invitations (including a repeated one), role merging and changes, the project owner guards, validation errors, and deletion with and without confirmation.user:getat the environment level, for an unknown user, and with the deprecated--roleoption.organization:user:add/update/delete/get/list: invitation, adding an existing user, permission changes, "already set", the owner guard, and deletion with and without confirmation.team:create(roles,--output-id, label uniqueness and conflicts),team:get/list/update/delete,team:project:add/delete/list,team:user:add/delete/list.🤖 Generated with Claude Code