authorize('manageMembers', $collection); $data = $request->validate([ 'username' => ['required', 'string', 'min:3', 'max:20'], 'role' => ['required', 'in:editor,contributor,viewer'], 'note' => ['nullable', 'string', 'max:320'], 'expires_in_days' => ['nullable', 'integer', 'min:1', 'max:90'], 'expires_at' => ['nullable', 'date', 'after:now'], ]); $invitee = User::query() ->whereRaw('LOWER(username) = ?', [strtolower((string) $data['username'])]) ->firstOrFail(); $member = $this->collaborators->inviteMember( $collection, $request->user(), $invitee, (string) $data['role'], $data['note'] ?? null, isset($data['expires_in_days']) ? (int) $data['expires_in_days'] : null, $data['expires_at'] ?? null, ); return response()->json([ 'ok' => true, 'member' => $member, 'members' => $this->collaborators->mapMembers($collection, $request->user()), ]); } public function transfer(Request $request, Collection $collection, CollectionMember $member): JsonResponse { $collection = $this->collaborators->transferOwnership($collection, $member, $request->user()); return response()->json([ 'ok' => true, 'collection' => $this->collections->mapCollectionDetailPayload($collection->loadMissing('user'), true), 'members' => $this->collaborators->mapMembers($collection, $request->user()), ]); } public function update(Request $request, Collection $collection, CollectionMember $member): JsonResponse { $this->authorize('manageMembers', $collection); abort_unless((int) $member->collection_id === (int) $collection->id, 404); $data = $request->validate([ 'role' => ['required', 'in:editor,contributor,viewer'], ]); $this->collaborators->updateMemberRole($member, $request->user(), (string) $data['role']); return response()->json([ 'ok' => true, 'members' => $this->collaborators->mapMembers($collection, $request->user()), ]); } public function destroy(Request $request, Collection $collection, CollectionMember $member): JsonResponse { $this->authorize('manageMembers', $collection); abort_unless((int) $member->collection_id === (int) $collection->id, 404); $this->collaborators->revokeMember($member, $request->user()); return response()->json([ 'ok' => true, 'members' => $this->collaborators->mapMembers($collection, $request->user()), ]); } public function accept(Request $request, CollectionMember $member): JsonResponse { $collection = $member->collection; $this->collaborators->acceptInvite($member, $request->user()); return response()->json([ 'ok' => true, 'members' => $this->collaborators->mapMembers($collection, $request->user()), ]); } public function decline(Request $request, CollectionMember $member): JsonResponse { $collection = $member->collection; $this->collaborators->declineInvite($member, $request->user()); return response()->json([ 'ok' => true, 'members' => $this->collaborators->mapMembers($collection, $request->user()), ]); } }