summaryrefslogtreecommitdiffstats
path: root/lib
diff options
context:
space:
mode:
authorJoas Schilling <coding@schilljs.com>2023-01-31 16:06:05 +0100
committerJoas Schilling <coding@schilljs.com>2023-02-01 09:17:04 +0100
commit6150cb402e90ae7fc2cf6f30e964b464c3068e8f (patch)
treebe236095d6f746d01baa1b6a7d6c60424c69dab5 /lib
parentdef0f4f70486f3ad4e9b95c938f4abbf455591c4 (diff)
Add an endpoint to return all participants of a room with its breakout rooms
Signed-off-by: Joas Schilling <coding@schilljs.com>
Diffstat (limited to 'lib')
-rw-r--r--lib/Controller/RoomController.php33
-rw-r--r--lib/Participant.php4
-rw-r--r--lib/Service/ParticipantService.php44
3 files changed, 80 insertions, 1 deletions
diff --git a/lib/Controller/RoomController.php b/lib/Controller/RoomController.php
index 2f725cc00..0e44e69a4 100644
--- a/lib/Controller/RoomController.php
+++ b/lib/Controller/RoomController.php
@@ -699,9 +699,39 @@ class RoomController extends AEnvironmentAwareController {
return new DataResponse([], Http::STATUS_FORBIDDEN);
}
- $maxPingAge = $this->timeFactory->getTime() - Session::SESSION_TIMEOUT_KILL;
$participants = $this->participantService->getSessionsAndParticipantsForRoom($this->room);
+
+ return $this->formatParticipantList($participants, $includeStatus);
+ }
+
+ /**
+ * @PublicPage
+ * @RequireParticipant
+ * @RequireModeratorOrNoLobby
+ *
+ * @param bool $includeStatus
+ * @return DataResponse
+ */
+ public function getBreakoutRoomParticipants(bool $includeStatus = false): DataResponse {
+ if ($this->participant->getAttendee()->getParticipantType() === Participant::GUEST) {
+ return new DataResponse([], Http::STATUS_FORBIDDEN);
+ }
+
+ $breakoutRooms = $this->breakoutRoomService->getBreakoutRooms($this->room, $this->participant);
+ $breakoutRooms[] = $this->room;
+ $participants = $this->participantService->getSessionsAndParticipantsForRooms($breakoutRooms);
+
+ return $this->formatParticipantList($participants, $includeStatus);
+ }
+
+ /**
+ * @param Participant[] $participants
+ * @param bool $includeStatus
+ * @return DataResponse
+ */
+ protected function formatParticipantList(array $participants, bool $includeStatus): DataResponse {
$results = $headers = $statuses = [];
+ $maxPingAge = $this->timeFactory->getTime() - Session::SESSION_TIMEOUT_KILL;
if ($this->userId !== null
&& $includeStatus
@@ -747,6 +777,7 @@ class RoomController extends AEnvironmentAwareController {
}
$result = [
+ 'roomToken' => $participant->getRoom()->getToken(),
'inCall' => Participant::FLAG_DISCONNECTED,
'lastPing' => 0,
'sessionIds' => [],
diff --git a/lib/Participant.php b/lib/Participant.php
index 83e80f7f5..b11a9f74b 100644
--- a/lib/Participant.php
+++ b/lib/Participant.php
@@ -67,6 +67,10 @@ class Participant {
$this->session = $session;
}
+ public function getRoom(): Room {
+ return $this->room;
+ }
+
public function getAttendee(): Attendee {
return $this->attendee;
}
diff --git a/lib/Service/ParticipantService.php b/lib/Service/ParticipantService.php
index 2941972c8..f03fad5e6 100644
--- a/lib/Service/ParticipantService.php
+++ b/lib/Service/ParticipantService.php
@@ -1267,6 +1267,34 @@ class ParticipantService {
}
/**
+ * Get all sessions and attendees without a session for the room
+ *
+ * This will return multiple items for the same attendee if the attendee
+ * has multiple sessions in the room.
+ *
+ * @param Room[] $rooms
+ * @return Participant[]
+ */
+ public function getSessionsAndParticipantsForRooms(array $rooms): array {
+ $roomIds = array_map(static fn (Room $room) => $room->getId(), $rooms);
+ $map = array_combine($roomIds, $rooms);
+
+ $query = $this->connection->getQueryBuilder();
+
+ $helper = new SelectHelper();
+ $helper->selectAttendeesTable($query);
+ $helper->selectSessionsTable($query);
+ $query->from('talk_attendees', 'a')
+ ->leftJoin(
+ 'a', 'talk_sessions', 's',
+ $query->expr()->eq('s.attendee_id', 'a.id')
+ )
+ ->where($query->expr()->in('a.room_id', $query->createNamedParameter($roomIds, IQueryBuilder::PARAM_INT_ARRAY)));
+
+ return $this->getParticipantsForRoomsFromQuery($query, $map);
+ }
+
+ /**
* @param Room $room
* @param int $maxAge
* @return Participant[]
@@ -1350,12 +1378,28 @@ class ParticipantService {
/**
* @param IQueryBuilder $query
+ * @param Room $room
* @return Participant[]
*/
protected function getParticipantsFromQuery(IQueryBuilder $query, Room $room): array {
+ return $this->getParticipantsForRoomsFromQuery($query, [$room->getId() => $room]);
+ }
+
+ /**
+ * @param IQueryBuilder $query
+ * @param Room[] $rooms Room ID => Room object
+ * @psalm-param array<int, Room> $rooms
+ * @return Participant[]
+ */
+ protected function getParticipantsForRoomsFromQuery(IQueryBuilder $query, array $rooms): array {
$participants = [];
$result = $query->executeQuery();
while ($row = $result->fetch()) {
+ $room = $rooms[(int) $row['room_id']] ?? null;
+ if ($room === null) {
+ continue;
+ }
+
$attendee = $this->attendeeMapper->createAttendeeFromRow($row);
if (isset($row['s_id'])) {
$session = $this->sessionMapper->createSessionFromRow($row);