Merge pull request #1286 from nextcloud/add-session-to-participant

Add session & participantFlags to participant
This commit is contained in:
Ivan Sein 2018-11-20 11:48:03 +01:00 коммит произвёл GitHub
Родитель d00f88f526 56e90228ab
Коммит 17135c9f87
Не найден ключ, соответствующий данной подписи
Идентификатор ключа GPG: 4AEE18F83AFDEB23
13 изменённых файлов: 157 добавлений и 141 удалений

Просмотреть файл

@ -77,8 +77,7 @@ class Hooks {
}
$duration = $this->timeFactory->getTime() - $activeSince->getTimestamp();
$participants = $room->getParticipants($activeSince->getTimestamp());
$userIds = array_map('\strval', array_keys($participants['users']));
$userIds = $room->getParticipantUserIds($activeSince->getTimestamp());
if (empty($userIds) || (\count($userIds) === 1 && $room->getActiveGuests() === 0)) {
// Single user pinged or guests only => no activity

Просмотреть файл

@ -58,10 +58,9 @@ class SearchPlugin implements ISearchPlugin {
* @since 13.0.0
*/
public function search($search, $limit, $offset, ISearchResult $searchResult) {
$participants = $this->room->getParticipants();
$this->searchUsers($search, array_map('strval', array_keys($participants['users'])), $searchResult);
// FIXME Handle guests
$this->searchUsers($search, $this->room->getParticipantUserIds(), $searchResult);
return false;
}

Просмотреть файл

@ -93,34 +93,19 @@ class CallController extends OCSController {
return new DataResponse([], Http::STATUS_NOT_FOUND);
}
/** @var array[] $participants */
$participants = $room->getParticipants(time() - 30);
$result = [];
foreach ($participants['users'] as $participant => $data) {
if ($data['sessionId'] === '0' || !$data['inCall']) {
$participants = $room->getParticipants(time() - 30);
foreach ($participants as $participant) {
if ($participant->getSessionId() === '0' || $participant->getInCallFlags() === Participant::FLAG_DISCONNECTED) {
// User is not active in call
continue;
}
$result[] = [
'userId' => (string) $participant,
'userId' => $participant->getUser(),
'token' => $token,
'lastPing' => $data['lastPing'],
'sessionId' => $data['sessionId'],
];
}
foreach ($participants['guests'] as $data) {
if (!$data['inCall']) {
// User is not active in call
continue;
}
$result[] = [
'userId' => '',
'token' => $token,
'lastPing' => $data['lastPing'],
'sessionId' => $data['sessionId'],
'lastPing' => $participant->getLastPing(),
'sessionId' => $participant->getSessionId(),
];
}

Просмотреть файл

@ -48,7 +48,6 @@ use OCP\IUserManager;
use OCP\IGroup;
use OCP\IGroupManager;
use OCP\Mail\IMailer;
use OCP\Share;
class RoomController extends OCSController {
/** @var string */
@ -166,16 +165,16 @@ class RoomController extends OCSController {
/**
* @param Room $room
* @param Participant $participant
* @param Participant $currentParticipant
* @return array
* @throws RoomNotFoundException
*/
protected function formatRoom(Room $room, Participant $participant = null): array {
protected function formatRoom(Room $room, Participant $currentParticipant = null): array {
if ($participant instanceof Participant) {
$participantType = $participant->getParticipantType();
$participantFlags = $participant->getInCallFlags();
$favorite = $participant->isFavorite();
if ($currentParticipant instanceof Participant) {
$participantType = $currentParticipant->getParticipantType();
$participantFlags = $currentParticipant->getInCallFlags();
$favorite = $currentParticipant->isFavorite();
} else {
$participantType = Participant::GUEST;
$participantFlags = Participant::FLAG_DISCONNECTED;
@ -218,12 +217,12 @@ class RoomController extends OCSController {
'lastMessage' => [],
];
if (!$participant instanceof Participant) {
if (!$currentParticipant instanceof Participant) {
return $roomData;
}
if ($participant->getNotificationLevel() !== Participant::NOTIFY_DEFAULT) {
$roomData['notificationLevel'] = $participant->getNotificationLevel();
if ($currentParticipant->getNotificationLevel() !== Participant::NOTIFY_DEFAULT) {
$roomData['notificationLevel'] = $currentParticipant->getNotificationLevel();
}
if ($room->getObjectType() === 'share:password') {
@ -234,44 +233,46 @@ class RoomController extends OCSController {
$currentUser = $this->userManager->get($this->userId);
if ($currentUser instanceof IUser) {
$unreadSince = $this->chatManager->getUnreadMarker($room, $currentUser);
if ($participant instanceof Participant) {
$lastMention = $participant->getLastMention();
if ($currentParticipant instanceof Participant) {
$lastMention = $currentParticipant->getLastMention();
$roomData['unreadMention'] = $lastMention !== null && $unreadSince < $lastMention;
}
$roomData['unreadMessages'] = $this->chatManager->getUnreadCount($room, $unreadSince);
}
// Sort by lastPing
/** @var array[] $participants */
$participants = $room->getParticipants();
$sortParticipants = function(array $participant1, array $participant2) {
return $participant2['lastPing'] - $participant1['lastPing'];
};
uasort($participants['users'], $sortParticipants);
uasort($participants['guests'], $sortParticipants);
$numActiveGuests = 0;
$cleanGuests = false;
$participantList = [];
foreach ($participants['users'] as $userId => $data) {
$user = $this->userManager->get((string) $userId);
if ($user instanceof IUser) {
$participantList[(string) $user->getUID()] = [
'name' => $user->getDisplayName(),
'type' => $data['participantType'],
'call' => $data['inCall'],
];
}
$participants = $room->getParticipants();
uasort($participants, function(Participant $participant1, Participant $participant2) {
return $participant2->getLastPing() - $participant1->getLastPing();
});
if ($data['sessionId'] !== '0' && $data['lastPing'] <= time() - 100) {
$room->leaveRoom((string) $userId);
foreach ($participants as $participant) {
if ($participant->isGuest()) {
if ($participant->getLastPing() <= time() - 100) {
$cleanGuests = true;
} else {
$numActiveGuests++;
}
} else {
$user = $this->userManager->get($participant->getUser());
if ($user instanceof IUser) {
$participantList[(string)$user->getUID()] = [
'name' => $user->getDisplayName(),
'type' => $participant->getParticipantType(),
'call' => $participant->getInCallFlags(),
'sessionId' => $participant->getSessionId(),
];
}
if ($participant->getSessionId() !== '0' && $participant->getLastPing() <= time() - 100) {
$room->leaveRoom($participant->getUser());
}
}
}
$activeGuests = array_filter($participants['guests'], function($data) {
return $data['lastPing'] > time() - 100;
});
$numActiveGuests = \count($activeGuests);
if ($numActiveGuests !== \count($participants['guests'])) {
if ($cleanGuests) {
$room->cleanGuestParticipants();
}
@ -283,8 +284,8 @@ class RoomController extends OCSController {
}
$roomData = array_merge($roomData, [
'lastPing' => $participant->getLastPing(),
'sessionId' => $participant->getSessionId(),
'lastPing' => $currentParticipant->getLastPing(),
'sessionId' => $currentParticipant->getSessionId(),
'participants' => $participantList,
'numGuests' => $numActiveGuests,
'lastMessage' => $lastMessage,
@ -705,7 +706,7 @@ class RoomController extends OCSController {
return new DataResponse([], Http::STATUS_FORBIDDEN);
}
$participants = $room->getParticipants();
$participants = $room->getParticipantsLegacy();
$results = [];
foreach ($participants['users'] as $userId => $participant) {
@ -759,7 +760,7 @@ class RoomController extends OCSController {
return new DataResponse([], Http::STATUS_FORBIDDEN);
}
$participants = $room->getParticipants();
$participants = $room->getParticipantUserIds();
$updateRoomType = $room->getType() === Room::ONE_TO_ONE_CALL ? Room::GROUP_CALL : false;
$participantsToAdd = [];
@ -769,7 +770,7 @@ class RoomController extends OCSController {
return new DataResponse([], Http::STATUS_NOT_FOUND);
}
if (isset($participants['users'][$newParticipant])) {
if (\in_array($newParticipant, $participants, true)) {
return new DataResponse([]);
}
@ -784,7 +785,7 @@ class RoomController extends OCSController {
$usersInGroup = $group->getUsers();
foreach ($usersInGroup as $user) {
if (isset($participants['users'][$user->getUID()])) {
if (\in_array($user->getUID(), $participants, true)) {
continue;
}

Просмотреть файл

@ -210,32 +210,21 @@ class SignalingController extends OCSController {
* @param Room $room
* @return array[]
*/
protected function getUsersInRoom(Room $room) {
protected function getUsersInRoom(Room $room): array {
$usersInRoom = [];
$participants = $room->getParticipants(time() - 30);
foreach ($participants['users'] as $participant => $data) {
if ($data['sessionId'] === '0') {
foreach ($participants as $participant) {
if ($participant->getSessionId() === '0') {
// User is not active
continue;
}
$usersInRoom[] = [
'userId' => $participant,
'userId' => $participant->getUser(),
'roomId' => $room->getId(),
'lastPing' => $data['lastPing'],
'sessionId' => $data['sessionId'],
'inCall' => $data['inCall'],
];
}
foreach ($participants['guests'] as $data) {
$usersInRoom[] = [
'userId' => '',
'roomId' => $room->getId(),
'lastPing' => $data['lastPing'],
'sessionId' => $data['sessionId'],
'inCall' => $data['inCall'],
'lastPing' => $participant->getLastPing(),
'sessionId' => $participant->getSessionId(),
'inCall' => $participant->getInCallFlags(),
];
}

Просмотреть файл

@ -43,14 +43,7 @@ class HookListener {
if ($room->getType() === Room::ONE_TO_ONE_CALL || $room->getNumberOfParticipants() === 1) {
$room->deleteRoom();
} else {
$particiants = $room->getParticipants();
// Also delete the room, when the user is the only non-guest user
if (\count($particiants['users']) === 1) {
$room->deleteRoom();
} else {
$room->removeUser($user);
}
$room->removeUser($user);
}
}
}

Просмотреть файл

@ -24,6 +24,7 @@ declare(strict_types=1);
namespace OCA\Spreed\PublicShareAuth;
use OCA\Spreed\Exceptions\ParticipantNotFoundException;
use OCA\Spreed\Participant;
use OCA\Spreed\Room;
use Symfony\Component\EventDispatcher\EventDispatcherInterface;
@ -92,15 +93,15 @@ class Listener {
return;
}
$participants = $room->getParticipants();
$users = $participants['users'];
$guests = $participants['guests'];
if (array_key_exists($userId, $users) && $users[$userId]['participantType'] === Participant::OWNER) {
return;
try {
$participant = $room->getParticipant($userId);
if ($participant->getParticipantType() === Participant::OWNER) {
return;
}
} catch (ParticipantNotFoundException $e) {
}
if (\count($users) > 1 || \count($guests) > 0) {
if ($room->getActiveGuests() > 0 || \count($room->getParticipantUserIds()) > 1) {
throw new \OverflowException('Only the owner and another participant are allowed in rooms to request the password for a share');
}
}
@ -119,11 +120,7 @@ class Listener {
return;
}
$participants = $room->getParticipants();
$users = $participants['users'];
$guests = $participants['guests'];
if (\count($users) > 1 || \count($guests) > 0) {
if ($room->getActiveGuests() > 0 || \count($room->getParticipantUserIds()) > 1) {
throw new \OverflowException('Only the owner and another participant are allowed in rooms to request the password for a share');
}
}

Просмотреть файл

@ -272,7 +272,7 @@ class Room {
}
public function deleteRoom() {
$participants = $this->getParticipants();
$participants = $this->getParticipantsLegacy();
$this->dispatcher->dispatch(self::class . '::preDeleteRoom', new GenericEvent($this, [
'participants' => $participants,
]));
@ -787,9 +787,35 @@ class Room {
/**
* @param int $lastPing When the last ping is older than the given timestamp, the user is ignored
* @return array[] Array of users with [users => [userId => [lastPing, sessionId]], guests => [[lastPing, sessionId]]]
* @return Participant[]
*/
public function getParticipants($lastPing = 0) {
public function getParticipants($lastPing = 0): array {
$query = $this->db->getQueryBuilder();
$query->select('*')
->from('talk_participants')
->where($query->expr()->eq('room_id', $query->createNamedParameter($this->getId(), IQueryBuilder::PARAM_INT)));
if ($lastPing > 0) {
$query->andWhere($query->expr()->gt('last_ping', $query->createNamedParameter($lastPing, IQueryBuilder::PARAM_INT)));
}
$result = $query->execute();
$participants = [];
while ($row = $result->fetch()) {
$participants[] = $this->manager->createParticipantObject($this, $row);
}
$result->closeCursor();
return $participants;
}
/**
* @param int $lastPing When the last ping is older than the given timestamp, the user is ignored
* @return array[] Array of users with [users => [userId => [lastPing, sessionId]], guests => [[lastPing, sessionId]]]
* @deprecated Use self::getParticipants() instead
*/
public function getParticipantsLegacy($lastPing = 0): array {
$query = $this->db->getQueryBuilder();
$query->select('*')
->from('talk_participants')
@ -827,6 +853,32 @@ class Room {
];
}
/**
* @param int $lastPing When the last ping is older than the given timestamp, the user is ignored
* @return string[]
*/
public function getParticipantUserIds(int $lastPing = 0): array {
$query = $this->db->getQueryBuilder();
$query->select('user_id')
->from('talk_participants')
->where($query->expr()->eq('room_id', $query->createNamedParameter($this->getId(), IQueryBuilder::PARAM_INT)))
->andWhere($query->expr()->nonEmptyString('user_id'));
if ($lastPing > 0) {
$query->andWhere($query->expr()->gt('last_ping', $query->createNamedParameter($lastPing, IQueryBuilder::PARAM_INT)));
}
$result = $query->execute();
$users = [];
while ($row = $result->fetch()) {
$users[] = $row['user_id'];
}
$result->closeCursor();
return $users;
}
/**
* @param int $notificationLevel
* @return Participant[] Array of participants

Просмотреть файл

@ -27,6 +27,7 @@ namespace OCA\Spreed\Share\Helper;
use OCA\Spreed\Exceptions\RoomNotFoundException;
use OCA\Spreed\Manager;
use OCA\Spreed\Room;
use OCP\IUser;
use OCP\IUserManager;
use OCP\Share\IShare;
@ -87,10 +88,15 @@ class DeletedShareAPIController {
// the other participant.
$roomName = $room->getName();
if ($room->getType() === Room::ONE_TO_ONE_CALL) {
$participantsList = $room->getParticipants()['users'];
unset($participantsList[$this->userId]);
$roomName = $this->userManager->get(key($participantsList))->getDisplayName();
$userIds = $room->getParticipantUserIds();
foreach ($userIds as $userId) {
if ($this->userId !== $userId) {
$user = $this->userManager->get($userId);
if ($user instanceof IUser) {
$roomName = $user->getDisplayName();
}
}
}
}
$result['share_with_displayname'] = $roomName;

Просмотреть файл

@ -30,6 +30,7 @@ use OCA\Spreed\Manager;
use OCA\Spreed\Room;
use OCP\AppFramework\OCS\OCSNotFoundException;
use OCP\IL10N;
use OCP\IUser;
use OCP\IUserManager;
use OCP\Share\IShare;
@ -94,10 +95,15 @@ class ShareAPIController {
// the other participant.
$roomName = $room->getName();
if ($room->getType() === Room::ONE_TO_ONE_CALL) {
$participantsList = $room->getParticipants()['users'];
unset($participantsList[$this->userId]);
$roomName = $this->userManager->get(key($participantsList))->getDisplayName();
$userIds = $room->getParticipantUserIds();
foreach ($userIds as $userId) {
if ($this->userId !== $userId) {
$user = $this->userManager->get($userId);
if ($user instanceof IUser) {
$roomName = $user->getDisplayName();
}
}
}
}
$result['share_with_displayname'] = $roomName;

Просмотреть файл

@ -938,14 +938,14 @@ class RoomShareProvider implements IShareProvider {
continue;
}
$userList = $room->getParticipants()['users'];
foreach ($userList as $uid => $participantData) {
$users[$uid] = isset($users[$uid]) ? $users[$uid] : [];
$userList = $room->getParticipantUserIds();
foreach ($userList as $uid) {
$users[$uid] = $users[$uid] ?? [];
$users[$uid][$row['id']] = $row;
}
} else if ($type === self::SHARE_TYPE_USERROOM && $currentAccess === true) {
$uid = $row['share_with'];
$users[$uid] = isset($users[$uid]) ? $users[$uid] : [];
$users[$uid] = $users[$uid] ?? [];
$users[$uid][$row['id']] = $row;
}
}

Просмотреть файл

@ -112,17 +112,6 @@ class BackendNotifier{
$this->doRequest($url, $params);
}
/**
* Return list of userids that are invited to a room.
*
* @param Room $room
* @return array
*/
private function getRoomUserIds($room) {
$participants = $room->getParticipants();
return array_keys($participants['users']);
}
/**
* The given users are now invited to a room.
*
@ -142,7 +131,7 @@ class BackendNotifier{
'userids' => $userIds,
// TODO(fancycode): We should try to get rid of 'alluserids' and
// find a better way to notify existing users to update the room.
'alluserids' => $this->getRoomUserIds($room),
'alluserids' => $room->getParticipantUserIds(),
'properties' => [
'name' => $room->getName(),
'type' => $room->getType(),
@ -166,7 +155,7 @@ class BackendNotifier{
'userids' => $userIds,
// TODO(fancycode): We should try to get rid of 'alluserids' and
// find a better way to notify existing users to update the room.
'alluserids' => $this->getRoomUserIds($room),
'alluserids' => $room->getParticipantUserIds(),
'properties' => [
'name' => $room->getName(),
'type' => $room->getType(),
@ -190,7 +179,7 @@ class BackendNotifier{
'sessionids' => $sessionIds,
// TODO(fancycode): We should try to get rid of 'alluserids' and
// find a better way to notify existing users to update the room.
'alluserids' => $this->getRoomUserIds($room),
'alluserids' => $room->getParticipantUserIds(),
'properties' => [
'name' => $room->getName(),
'type' => $room->getType(),
@ -210,7 +199,7 @@ class BackendNotifier{
$this->backendRequest('/api/v1/room/' . $room->getToken(), [
'type' => 'update',
'update' => [
'userids' => $this->getRoomUserIds($room),
'userids' => $room->getParticipantUserIds(),
'properties' => [
'name' => $room->getName(),
'type' => $room->getType(),
@ -246,7 +235,7 @@ class BackendNotifier{
$this->logger->info('Room participants modified: ' . $room->getToken() . ' ' . print_r($sessionIds, true), ['app' => 'spreed']);
$changed = [];
$users = [];
$participants = $room->getParticipants();
$participants = $room->getParticipantsLegacy();
foreach ($participants['users'] as $userId => $participant) {
$participant['userId'] = $userId;
$users[] = $participant;
@ -284,7 +273,7 @@ class BackendNotifier{
$this->logger->info('Room in-call status changed: ' . $room->getToken() . ' ' . $flags . ' ' . print_r($sessionIds, true), ['app' => 'spreed']);
$changed = [];
$users = [];
$participants = $room->getParticipants();
$participants = $room->getParticipantsLegacy();
foreach ($participants['users'] as $userId => $participant) {
$participant['userId'] = $userId;
if ($participant['inCall'] !== Participant::FLAG_DISCONNECTED) {

Просмотреть файл

@ -71,8 +71,8 @@ class SearchPluginTest extends \Test\TestCase {
$room = $this->createMock(Room::class);
$room->expects($this->once())
->method('getParticipants')
->willReturn(['users' => [123 => [], 'foo' => [], 'bar' => []]]);
->method('getParticipantUserIds')
->willReturn(['123', 'foo', 'bar']);
$plugin = $this->getPlugin(['searchUsers']);
$plugin->setContext(['room' => $room]);