Welcome to mirror list, hosted at ThFree Co, Russian Federation.

github.com/nextcloud/spreed.git - Unnamed repository; edit this file 'description' to name the repository.
summaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorJoas Schilling <213943+nickvergessen@users.noreply.github.com>2022-06-13 13:37:39 +0300
committerGitHub <noreply@github.com>2022-06-13 13:37:39 +0300
commit84a30c9ba8e511cd71f6184c4a13637e9e648dd8 (patch)
treee2aa95425f3ac5ed2395fbcbe29dd5b24518c1d4
parent8b23801abc8719b1e7822621b3a0cc0a6f378ee8 (diff)
parentbe00d4e42c3df1778a1ab71bce78ec75f3ba5cda (diff)
Merge pull request #7464 from nextcloud/bugfix/noid/fix-next-federation-step
Test remote invite notifications and try to send the accept/decline on invites
-rw-r--r--lib/Chat/Parser/SystemMessage.php38
-rw-r--r--lib/Chat/SystemMessage/Listener.php7
-rw-r--r--lib/Federation/CloudFederationProviderTalk.php41
-rw-r--r--lib/Notification/Notifier.php18
-rw-r--r--tests/integration/features/bootstrap/FeatureContext.php74
-rw-r--r--tests/integration/features/federation/invite.feature54
-rwxr-xr-xtests/integration/run.sh21
-rw-r--r--tests/php/Chat/Parser/SystemMessageTest.php6
-rw-r--r--tests/php/Federation/FederationTest.php10
-rw-r--r--tests/php/Notification/NotifierTest.php17
10 files changed, 247 insertions, 39 deletions
diff --git a/lib/Chat/Parser/SystemMessage.php b/lib/Chat/Parser/SystemMessage.php
index 68a794406..fa10556de 100644
--- a/lib/Chat/Parser/SystemMessage.php
+++ b/lib/Chat/Parser/SystemMessage.php
@@ -34,6 +34,7 @@ use OCA\Talk\Participant;
use OCA\Talk\Room;
use OCA\Talk\Share\RoomShareProvider;
use OCP\Comments\IComment;
+use OCP\Federation\ICloudIdManager;
use OCP\Files\InvalidPathException;
use OCP\Files\IRootFolder;
use OCP\Files\Node;
@@ -57,6 +58,7 @@ class SystemMessage {
protected RoomShareProvider $shareProvider;
protected PhotoCache $photoCache;
protected IRootFolder $rootFolder;
+ protected ICloudIdManager $cloudIdManager;
protected IURLGenerator $url;
protected ?IL10N $l = null;
@@ -80,6 +82,7 @@ class SystemMessage {
RoomShareProvider $shareProvider,
PhotoCache $photoCache,
IRootFolder $rootFolder,
+ ICloudIdManager $cloudIdManager,
IURLGenerator $url) {
$this->userManager = $userManager;
$this->groupManager = $groupManager;
@@ -88,6 +91,7 @@ class SystemMessage {
$this->shareProvider = $shareProvider;
$this->photoCache = $photoCache;
$this->rootFolder = $rootFolder;
+ $this->cloudIdManager = $cloudIdManager;
$this->url = $url;
}
@@ -285,6 +289,26 @@ class SystemMessage {
$parsedMessage = $this->l->t('An administrator removed {user}');
}
}
+ } elseif ($message === 'federated_user_added') {
+ $parsedParameters['federated_user'] = $this->getRemoteUser($parameters['federated_user']);
+ $parsedMessage = $this->l->t('{actor} invited {user}');
+ if ($currentUserIsActor) {
+ $parsedMessage = $this->l->t('You invited {user}');
+ } elseif ($cliIsActor) {
+ $parsedMessage = $this->l->t('An administrator invited {user}');
+ } elseif ($parsedParameters['federated_user']['id'] === $parsedParameters['actor']['id']) {
+ $parsedMessage = $this->l->t('{federated_user} accepted the invitation');
+ }
+ } elseif ($message === 'federated_user_removed') {
+ $parsedParameters['federated_user'] = $this->getRemoteUser($parameters['federated_user']);
+ $parsedMessage = $this->l->t('{actor} removed {federated_user}');
+ if ($currentUserIsActor) {
+ $parsedMessage = $this->l->t('You removed {federated_user}');
+ } elseif ($cliIsActor) {
+ $parsedMessage = $this->l->t('An administrator removed {federated_user}');
+ } elseif ($parsedParameters['federated_user']['id'] === $parsedParameters['actor']['id']) {
+ $parsedMessage = $this->l->t('{federated_user} declined the invitation');
+ }
} elseif ($message === 'group_added') {
$parsedParameters['group'] = $this->getGroup($parameters['group']);
$parsedMessage = $this->l->t('{actor} added group {group}');
@@ -588,6 +612,9 @@ class SystemMessage {
if ($actorType === Attendee::ACTOR_GUESTS) {
return $this->getGuest($room, $actorId);
}
+ if ($actorType === Attendee::ACTOR_FEDERATED_USERS) {
+ return $this->getRemoteUser($actorId);
+ }
return $this->getUser($actorId);
}
@@ -616,6 +643,17 @@ class SystemMessage {
];
}
+ protected function getRemoteUser(string $federationId): array {
+ $cloudId = $this->cloudIdManager->resolveCloudId($federationId);
+
+ return [
+ 'type' => 'user',
+ 'id' => $cloudId->getUser(),
+ 'name' => $cloudId->getDisplayId(),
+ 'server' => $cloudId->getRemote(),
+ ];
+ }
+
protected function getDisplayName(string $uid): string {
$user = $this->userManager->get($uid);
if ($user instanceof IUser) {
diff --git a/lib/Chat/SystemMessage/Listener.php b/lib/Chat/SystemMessage/Listener.php
index e0ceb60ac..b58b7d175 100644
--- a/lib/Chat/SystemMessage/Listener.php
+++ b/lib/Chat/SystemMessage/Listener.php
@@ -370,6 +370,8 @@ class Listener implements IEventListener {
$this->sendSystemMessage($event->getRoom(), 'group_added', ['group' => $attendee->getActorId()]);
} elseif ($attendee->getActorType() === Attendee::ACTOR_CIRCLES) {
$this->sendSystemMessage($event->getRoom(), 'circle_added', ['circle' => $attendee->getActorId()]);
+ } elseif ($attendee->getActorType() === Attendee::ACTOR_FEDERATED_USERS) {
+ $this->sendSystemMessage($event->getRoom(), 'federated_user_added', ['federated_user' => $attendee->getActorId()]);
}
}
}
@@ -380,6 +382,8 @@ class Listener implements IEventListener {
$this->sendSystemMessage($event->getRoom(), 'group_removed', ['group' => $attendee->getActorId()]);
} elseif ($attendee->getActorType() === Attendee::ACTOR_CIRCLES) {
$this->sendSystemMessage($event->getRoom(), 'circle_removed', ['circle' => $attendee->getActorId()]);
+ } elseif ($attendee->getActorType() === Attendee::ACTOR_FEDERATED_USERS) {
+ $this->sendSystemMessage($event->getRoom(), 'federated_user_removed', ['federated_user' => $attendee->getActorId()]);
}
}
}
@@ -399,6 +403,9 @@ class Listener implements IEventListener {
} elseif ($this->session->exists('talk-overwrite-actor')) {
$actorType = Attendee::ACTOR_USERS;
$actorId = $this->session->get('talk-overwrite-actor');
+ } elseif ($this->session->exists('talk-overwrite-actor-type')) {
+ $actorType = $this->session->get('talk-overwrite-actor-type');
+ $actorId = $this->session->get('talk-overwrite-actor-id');
} else {
$actorType = Attendee::ACTOR_GUESTS;
$sessionId = $this->talkSession->getSessionForRoom($room->getToken());
diff --git a/lib/Federation/CloudFederationProviderTalk.php b/lib/Federation/CloudFederationProviderTalk.php
index 9ec518de2..9c1c0dd38 100644
--- a/lib/Federation/CloudFederationProviderTalk.php
+++ b/lib/Federation/CloudFederationProviderTalk.php
@@ -29,6 +29,7 @@ use Exception;
use OCA\FederatedFileSharing\AddressHandler;
use OCA\Talk\AppInfo\Application;
use OCA\Talk\Config;
+use OCA\Talk\Events\AttendeesAddedEvent;
use OCA\Talk\Manager;
use OCA\Talk\Model\Attendee;
use OCA\Talk\Model\AttendeeMapper;
@@ -37,6 +38,7 @@ use OCA\Talk\Room;
use OCA\Talk\Service\ParticipantService;
use OCP\AppFramework\Http;
use OCP\DB\Exception as DBException;
+use OCP\EventDispatcher\IEventDispatcher;
use OCP\Federation\Exceptions\ActionNotSupportedException;
use OCP\Federation\Exceptions\AuthenticationFailedException;
use OCP\Federation\Exceptions\BadRequestException;
@@ -44,11 +46,13 @@ use OCP\Federation\Exceptions\ProviderCouldNotAddShareException;
use OCP\Federation\ICloudFederationProvider;
use OCP\Federation\ICloudFederationShare;
use OCP\HintException;
+use OCP\ISession;
use OCP\IURLGenerator;
use OCP\IUser;
use OCP\IUserManager;
use OCP\Notification\IManager as INotificationManager;
use OCP\Share\Exceptions\ShareNotFound;
+use Psr\Log\LoggerInterface;
class CloudFederationProviderTalk implements ICloudFederationProvider {
private IUserManager $userManager;
@@ -68,6 +72,9 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
private AttendeeMapper $attendeeMapper;
private Manager $manager;
+ private ISession $session;
+ private IEventDispatcher $dispatcher;
+ private LoggerInterface $logger;
public function __construct(
IUserManager $userManager,
@@ -78,7 +85,10 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
IURLGenerator $urlGenerator,
ParticipantService $participantService,
AttendeeMapper $attendeeMapper,
- Manager $manager
+ Manager $manager,
+ ISession $session,
+ IEventDispatcher $dispatcher,
+ LoggerInterface $logger
) {
$this->userManager = $userManager;
$this->addressHandler = $addressHandler;
@@ -89,6 +99,9 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
$this->participantService = $participantService;
$this->attendeeMapper = $attendeeMapper;
$this->manager = $manager;
+ $this->session = $session;
+ $this->dispatcher = $dispatcher;
+ $this->logger = $logger;
}
/**
@@ -105,15 +118,18 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
*/
public function shareReceived(ICloudFederationShare $share): string {
if (!$this->config->isFederationEnabled()) {
+ $this->logger->debug('Received a federation invite but federation is disabled');
throw new ProviderCouldNotAddShareException('Server does not support talk federation', '', Http::STATUS_SERVICE_UNAVAILABLE);
}
if (!in_array($share->getShareType(), $this->getSupportedShareTypes(), true)) {
+ $this->logger->debug('Received a federation invite for invalid share type');
throw new ProviderCouldNotAddShareException('Support for sharing with non-users not implemented yet', '', Http::STATUS_NOT_IMPLEMENTED);
// TODO: Implement group shares
}
$roomType = $share->getProtocol()['roomType'];
if (!is_numeric($roomType) || !in_array((int) $roomType, $this->validSharedRoomTypes(), true)) {
+ $this->logger->debug('Received a federation invite for invalid room type');
throw new ProviderCouldNotAddShareException('roomType is not a valid number', '', Http::STATUS_BAD_REQUEST);
}
@@ -139,6 +155,7 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
if ($remote && $shareSecret && $shareWith && $roomToken && $remoteId && is_string($roomName) && $roomName && $owner) {
$shareWith = $this->userManager->get($shareWith);
if ($shareWith === null) {
+ $this->logger->debug('Received a federation invite for user that could not be found');
throw new ProviderCouldNotAddShareException('User does not exist', '', Http::STATUS_BAD_REQUEST);
}
@@ -147,6 +164,8 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
$this->notifyAboutNewShare($shareWith, $shareId, $sharedByFederatedId, $sharedBy, $roomName, $roomToken, $remote);
return $shareId;
}
+
+ $this->logger->debug('Received a federation invite with missing request data');
throw new ProviderCouldNotAddShareException('required request data not found', '', Http::STATUS_BAD_REQUEST);
}
@@ -183,7 +202,15 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
private function shareAccepted(int $id, array $notification): array {
$attendee = $this->getAttendeeAndValidate($id, $notification['sharedSecret']);
- // TODO: Add activity for share accepted
+ $this->session->set('talk-overwrite-actor-type', $attendee->getActorType());
+ $this->session->set('talk-overwrite-actor-id', $attendee->getActorId());
+
+ $room = $this->manager->getRoomById($attendee->getRoomId());
+ $event = new AttendeesAddedEvent($room, [$attendee]);
+ $this->dispatcher->dispatchTyped($event);
+
+ $this->session->remove('talk-overwrite-actor-type');
+ $this->session->remove('talk-overwrite-actor-id');
return [];
}
@@ -196,9 +223,15 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
private function shareDeclined(int $id, array $notification): array {
$attendee = $this->getAttendeeAndValidate($id, $notification['sharedSecret']);
+ $this->session->set('talk-overwrite-actor-type', $attendee->getActorType());
+ $this->session->set('talk-overwrite-actor-id', $attendee->getActorId());
+
$room = $this->manager->getRoomById($attendee->getRoomId());
$participant = new Participant($room, $attendee, null);
$this->participantService->removeAttendee($room, $participant, Room::PARTICIPANT_LEFT);
+
+ $this->session->remove('talk-overwrite-actor-type');
+ $this->session->remove('talk-overwrite-actor-id');
return [];
}
@@ -287,12 +320,12 @@ class CloudFederationProviderTalk implements ICloudFederationProvider {
$declineAction = $notification->createAction();
$declineAction->setLabel('decline')
- ->setLink($this->urlGenerator->linkToOCSRouteAbsolute('spreed.Federation.rejectShare', ['id' => $shareId]), 'DELETE');
+ ->setLink($this->urlGenerator->linkToOCSRouteAbsolute('spreed.Federation.rejectShare', ['apiVersion' => 'v1', 'id' => $shareId]), 'DELETE');
$notification->addAction($declineAction);
$acceptAction = $notification->createAction();
$acceptAction->setLabel('accept')
- ->setLink($this->urlGenerator->linkToOCSRouteAbsolute('spreed.Federation.acceptShare', ['id' => $shareId]), 'POST');
+ ->setLink($this->urlGenerator->linkToOCSRouteAbsolute('spreed.Federation.acceptShare', ['apiVersion' => 'v1', 'id' => $shareId]), 'POST');
$notification->addAction($acceptAction);
$this->notificationManager->notify($notification);
diff --git a/lib/Notification/Notifier.php b/lib/Notification/Notifier.php
index b069aead6..68af32113 100644
--- a/lib/Notification/Notifier.php
+++ b/lib/Notification/Notifier.php
@@ -213,6 +213,10 @@ class Notifier implements INotifier {
return $this->parseHostedSignalingServer($notification, $l);
}
+ if ($notification->getObjectType() === 'remote_talk_share') {
+ return $this->parseRemoteInvitationMessage($notification, $l);
+ }
+
try {
$room = $this->getRoom($notification->getObjectId(), $userId);
} catch (RoomNotFoundException $e) {
@@ -252,10 +256,6 @@ class Notifier implements INotifier {
return $this->parseChatMessage($notification, $room, $participant, $l);
}
- if ($subject === 'remote_talk_share') {
- return $this->parseRemoteInvitationMessage($notification, $l);
- }
-
$this->notificationManager->markProcessed($notification);
throw new \InvalidArgumentException('Unknown subject');
}
@@ -300,11 +300,15 @@ class Notifier implements INotifier {
$placeholders = $replacements = [];
foreach ($rosParameters as $placeholder => $parameter) {
$placeholders[] = '{' . $placeholder .'}';
- $replacements[] = $parameter['name'];
+ if ($parameter['type'] === 'user') {
+ $replacements[] = '@' . $parameter['name'];
+ } else {
+ $replacements[] = $parameter['name'];
+ }
}
- $notification->setParsedMessage(str_replace($placeholders, $replacements, $message));
- $notification->setRichMessage($message, $rosParameters);
+ $notification->setParsedSubject(str_replace($placeholders, $replacements, $message));
+ $notification->setRichSubject($message, $rosParameters);
return $notification;
}
diff --git a/tests/integration/features/bootstrap/FeatureContext.php b/tests/integration/features/bootstrap/FeatureContext.php
index 6e741187f..ca7e67874 100644
--- a/tests/integration/features/bootstrap/FeatureContext.php
+++ b/tests/integration/features/bootstrap/FeatureContext.php
@@ -52,6 +52,10 @@ class FeatureContext implements Context, SnippetAcceptingContext {
protected static $textToMessageId;
/** @var array[] */
protected static $messageIdToText;
+ /** @var int[] */
+ protected static $remoteToInviteId;
+ /** @var string[] */
+ protected static $inviteIdToRemote;
protected static $permissionsMap = [
@@ -360,6 +364,32 @@ class FeatureContext implements Context, SnippetAcceptingContext {
}
$this->assertInvites($invites, $formData);
+
+ foreach ($invites as $data) {
+ self::$remoteToInviteId[$this->translateRemoteServer($data['remote_server']) . '::' . self::$tokenToIdentifier[$data['remote_token']]] = $data['id'];
+ self::$inviteIdToRemote[$data['id']] = $this->translateRemoteServer($data['remote_server']) . '::' . self::$tokenToIdentifier[$data['remote_token']];
+ }
+ }
+
+ /**
+ * @Then /^user "([^"]*)" (accepts|declines) invite to room "([^"]*)" of server "([^"]*)" \((v1)\)$/
+ *
+ * @param string $user
+ * @param string $roomName
+ * @param string $server
+ * @param string $apiVersion
+ * @param TableNode|null $formData
+ */
+ public function userAcceptsDeclinesRemoteInvite(string $user, string $acceptsDeclines, string $roomName, string $server, string $apiVersion, TableNode $formData = null): void {
+ $inviteId = self::$remoteToInviteId[$server . '::' . $roomName];
+
+ $verb = $acceptsDeclines === 'accepts' ? 'POST' : 'DELETE';
+
+ $this->setCurrentUser($user);
+ if ($server === 'LOCAL') {
+ $this->sendRemoteRequest($verb, '/apps/spreed/api/' . $apiVersion . '/federation/invitation/' . $inviteId);
+ }
+ $this->assertStatusCode($this->response, 200);
}
/**
@@ -380,19 +410,24 @@ class FeatureContext implements Context, SnippetAcceptingContext {
$data['remote_token'] = self::$tokenToIdentifier[$invite['remote_token']] ?? 'unknown-token';
}
if (isset($expectedInvite['remote_server'])) {
- if ($invite['remote_server'] === 'localhost:8080') {
- $data['remote_server'] = 'LOCAL';
- } elseif ($invite['remote_server'] === 'localhost:8180') {
- $data['remote_server'] = 'REMOTE';
- } else {
- $data['remote_server'] = 'unknown-server';
- }
+ $data['remote_server'] = $this->translateRemoteServer($invite['remote_server']);
}
return $data;
}, $invites, $formData->getHash()));
}
+ protected function translateRemoteServer(string $server): string {
+ $server = str_replace('http://', '', $server);
+ if ($server === 'localhost:8080') {
+ return 'LOCAL';
+ }
+ if ($server === 'localhost:8180') {
+ return 'REMOTE';
+ }
+ return 'unknown-server';
+ }
+
/**
* @Then /^user "([^"]*)" (is|is not) participant of room "([^"]*)" \((v4)\)$/
*
@@ -1783,7 +1818,7 @@ class FeatureContext implements Context, SnippetAcceptingContext {
$data = [
'room' => self::$tokenToIdentifier[$message['token']],
'actorType' => (string) $message['actorType'],
- 'actorId' => ($message['actorType'] === 'guests') ? self::$sessionIdToUser[$message['actorId']]: (string) $message['actorId'],
+ 'actorId' => ($message['actorType'] === 'guests') ? self::$sessionIdToUser[$message['actorId']] : (string) $message['actorId'],
'systemMessage' => (string) $message['systemMessage'],
];
@@ -2006,6 +2041,8 @@ class FeatureContext implements Context, SnippetAcceptingContext {
if (strpos($notification['object_id'], '/') !== false) {
[$roomToken, $message] = explode('/', $notification['object_id']);
$data['object_id'] = self::$tokenToIdentifier[$roomToken] . '/' . self::$messageIdToText[$message] ?? 'UNKNOWN_MESSAGE';
+ } elseif (strpos($expectedNotification['object_id'], 'INVITE_ID') !== false) {
+ $data['object_id'] = 'INVITE_ID(' . self::$inviteIdToRemote[$notification['object_id']] . ')';
} else {
[$roomToken,] = explode('/', $notification['object_id']);
$data['object_id'] = self::$tokenToIdentifier[$roomToken];
@@ -2414,6 +2451,27 @@ class FeatureContext implements Context, SnippetAcceptingContext {
*/
public function sendRequest($verb, $url, $body = null, array $headers = []) {
$fullUrl = $this->baseUrl . 'ocs/v2.php' . $url;
+ $this->sendRequestFullUrl($verb, $fullUrl, $body, $headers);
+ }
+
+ /**
+ * @param string $verb
+ * @param string $url
+ * @param TableNode|array|null $body
+ * @param array $headers
+ */
+ public function sendRemoteRequest($verb, $url, $body = null, array $headers = []) {
+ $fullUrl = $this->baseRemoteUrl . 'ocs/v2.php' . $url;
+ $this->sendRequestFullUrl($verb, $fullUrl, $body, $headers);
+ }
+
+ /**
+ * @param string $verb
+ * @param string $fullUrl
+ * @param TableNode|array|null $body
+ * @param array $headers
+ */
+ public function sendRequestFullUrl($verb, $fullUrl, $body = null, array $headers = []) {
$client = new Client();
$options = ['cookies' => $this->getUserCookieJar($this->currentUser)];
if ($this->currentUser === 'admin') {
diff --git a/tests/integration/features/federation/invite.feature b/tests/integration/features/federation/invite.feature
index 26f93e6bb..1ea48f739 100644
--- a/tests/integration/features/federation/invite.feature
+++ b/tests/integration/features/federation/invite.feature
@@ -3,7 +3,7 @@ Feature: federation/invite
Given user "participant1" exists
Given user "participant2" exists
- Scenario: federation is disabled
+ Scenario: Federation is disabled
Given the following "spreed" app config is set
| federation_enabled | no |
Given user "participant1" creates room "room" (v4)
@@ -14,7 +14,7 @@ Feature: federation/invite
| actorType | actorId | participantType |
| users | participant1 | 1 |
- Scenario: federation is enabled
+ Scenario: Accepting an invite
Given the following "spreed" app config is set
| federation_enabled | yes |
Given user "participant1" creates room "room" (v4)
@@ -25,6 +25,56 @@ Feature: federation/invite
| actorType | actorId | participantType |
| users | participant1 | 1 |
| federated_users | participant2 | 3 |
+ Then user "participant1" sees the following system messages in room "room" with 200
+ | room | actorType | actorId | systemMessage | message | messageParameters |
+ | room | users | participant1 | federated_user_added | You invited {user} | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"},"federated_user":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"}} |
+ | room | users | participant1 | conversation_created | You created the conversation | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"}} |
And user "participant2" has the following invitations (v1)
| remote_server | remote_token |
| LOCAL | room |
+ Then user "participant2" has the following notifications
+ | app | object_type | object_id | subject |
+ | spreed | remote_talk_share | INVITE_ID(LOCAL::room) | @participant1-displayname shared room room on http://localhost:8080 with you |
+ And user "participant2" accepts invite to room "room" of server "LOCAL" (v1)
+ And user "participant2" has the following invitations (v1)
+ When user "participant1" sees the following attendees in room "room" with 200 (v4)
+ | actorType | actorId | participantType |
+ | users | participant1 | 1 |
+ | federated_users | participant2 | 3 |
+ Then user "participant1" sees the following system messages in room "room" with 200
+ | room | actorType | actorId | systemMessage | message | messageParameters |
+ | room | federated_users | participant2@http://localhost:8180 | federated_user_added | {federated_user} accepted the invitation | {"actor":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"},"federated_user":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"}} |
+ | room | users | participant1 | federated_user_added | You invited {user} | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"},"federated_user":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"}} |
+ | room | users | participant1 | conversation_created | You created the conversation | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"}} |
+
+ Scenario: Declining an invite
+ Given the following "spreed" app config is set
+ | federation_enabled | yes |
+ Given user "participant1" creates room "room" (v4)
+ | roomType | 3 |
+ | roomName | room |
+ And user "participant1" adds remote "participant2" to room "room" with 200 (v4)
+ When user "participant1" sees the following attendees in room "room" with 200 (v4)
+ | actorType | actorId | participantType |
+ | users | participant1 | 1 |
+ | federated_users | participant2 | 3 |
+ Then user "participant1" sees the following system messages in room "room" with 200
+ | room | actorType | actorId | systemMessage | message | messageParameters |
+ | room | users | participant1 | federated_user_added | You invited {user} | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"},"federated_user":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"}} |
+ | room | users | participant1 | conversation_created | You created the conversation | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"}} |
+ And user "participant2" has the following invitations (v1)
+ | remote_server | remote_token |
+ | LOCAL | room |
+ Then user "participant2" has the following notifications
+ | app | object_type | object_id | subject |
+ | spreed | remote_talk_share | INVITE_ID(LOCAL::room) | @participant1-displayname shared room room on http://localhost:8080 with you |
+ And user "participant2" declines invite to room "room" of server "LOCAL" (v1)
+ And user "participant2" has the following invitations (v1)
+ When user "participant1" sees the following attendees in room "room" with 200 (v4)
+ | actorType | actorId | participantType |
+ | users | participant1 | 1 |
+ Then user "participant1" sees the following system messages in room "room" with 200
+ | room | actorType | actorId | systemMessage | message | messageParameters |
+ | room | federated_users | participant2@http://localhost:8180 | federated_user_removed | {federated_user} declined the invitation | {"actor":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"},"federated_user":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"}} |
+ | room | users | participant1 | federated_user_added | You invited {user} | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"},"federated_user":{"type":"user","id":"participant2","name":"participant2@localhost:8180","server":"http:\/\/localhost:8180"}} |
+ | room | users | participant1 | conversation_created | You created the conversation | {"actor":{"type":"user","id":"participant1","name":"participant1-displayname"}} |
diff --git a/tests/integration/run.sh b/tests/integration/run.sh
index ce3ebd25e..832032ba3 100755
--- a/tests/integration/run.sh
+++ b/tests/integration/run.sh
@@ -17,16 +17,25 @@ echo '#'
echo '# Starting PHP webserver'
echo '#'
php -S localhost:8080 -t ${ROOT_DIR} &
-PHPPID=$!
+PHPPID1=$!
echo 'Running on process ID:'
-echo $PHPPID
+echo $PHPPID1
# also kill php process in case of ctrl+c
-trap 'kill -TERM $PHPPID; wait $PHPPID' TERM
+trap 'kill -TERM $PHPPID1; wait $PHPPID1' TERM
# The federated server is started and stopped by the tests themselves
PORT_FED=8180
export PORT_FED
+
+php -S localhost:${PORT_FED} -t ${ROOT_DIR} &
+PHPPID2=$!
+echo 'Running on process ID:'
+echo $PHPPID2
+
+# also kill php process in case of ctrl+c
+trap 'kill -TERM $PHPPID2; wait $PHPPID2' TERM
+
NEXTCLOUD_ROOT_DIR=${ROOT_DIR}
export NEXTCLOUD_ROOT_DIR
export TEST_SERVER_URL="http://localhost:8080/"
@@ -74,11 +83,13 @@ echo ''
echo '#'
echo '# Stopping PHP webserver and disabling spreedcheats'
echo '#'
-kill $PHPPID
+kill $PHPPID1
+kill $PHPPID2
${ROOT_DIR}/occ app:disable spreedcheats
rm -rf ../../../spreedcheats
-wait $PHPPID
+wait $PHPPID1
+wait $PHPPID2
exit $RESULT
diff --git a/tests/php/Chat/Parser/SystemMessageTest.php b/tests/php/Chat/Parser/SystemMessageTest.php
index 1fcf409e0..ad9daae63 100644
--- a/tests/php/Chat/Parser/SystemMessageTest.php
+++ b/tests/php/Chat/Parser/SystemMessageTest.php
@@ -33,6 +33,7 @@ use OCA\Talk\Participant;
use OCA\Talk\Room;
use OCA\Talk\Share\RoomShareProvider;
use OCP\Comments\IComment;
+use OCP\Federation\ICloudIdManager;
use OCP\Files\Folder;
use OCP\Files\InvalidPathException;
use OCP\Files\IRootFolder;
@@ -71,6 +72,8 @@ class SystemMessageTest extends TestCase {
protected $rootFolder;
/** @var IURLGenerator|MockObject */
protected $url;
+ /** @var ICloudIdManager|MockObject */
+ protected $cloudIdManager;
/** @var IL10N|MockObject */
protected $l;
@@ -85,6 +88,7 @@ class SystemMessageTest extends TestCase {
$this->photoCache = $this->createMock(PhotoCache::class);
$this->rootFolder = $this->createMock(IRootFolder::class);
$this->url = $this->createMock(IURLGenerator::class);
+ $this->cloudIdManager = $this->createMock(ICloudIdManager::class);
$this->l = $this->createMock(IL10N::class);
$this->l->expects($this->any())
->method('t')
@@ -114,6 +118,7 @@ class SystemMessageTest extends TestCase {
$this->shareProvider,
$this->photoCache,
$this->rootFolder,
+ $this->cloudIdManager,
$this->url,
])
->onlyMethods($methods)
@@ -129,6 +134,7 @@ class SystemMessageTest extends TestCase {
$this->shareProvider,
$this->photoCache,
$this->rootFolder,
+ $this->cloudIdManager,
$this->url
);
}
diff --git a/tests/php/Federation/FederationTest.php b/tests/php/Federation/FederationTest.php
index 8bb7bd13d..0b6b6d147 100644
--- a/tests/php/Federation/FederationTest.php
+++ b/tests/php/Federation/FederationTest.php
@@ -34,10 +34,12 @@ use OCA\Talk\Model\AttendeeMapper;
use OCA\Talk\Room;
use OCA\Talk\Service\ParticipantService;
use OCP\BackgroundJob\IJobList;
+use OCP\EventDispatcher\IEventDispatcher;
use OCP\Federation\ICloudFederationFactory;
use OCP\Federation\ICloudFederationNotification;
use OCP\Federation\ICloudFederationProviderManager;
use OCP\Federation\ICloudFederationShare;
+use OCP\ISession;
use OCP\IURLGenerator;
use OCP\IUser;
use OCP\IUserManager;
@@ -84,11 +86,12 @@ class FederationTest extends TestCase {
$this->userManager = $this->createMock(IUserManager::class);
$this->attendeeMapper = $this->createMock(AttendeeMapper::class);
$this->config = $this->createMock(Config::class);
+ $this->logger = $this->createMock(LoggerInterface::class);
$this->notifications = new Notifications(
$this->cloudFederationFactory,
$this->addressHandler,
- $this->createMock(LoggerInterface::class),
+ $this->logger,
$this->cloudFederationProviderManager,
$this->createMock(IJobList::class),
$this->userManager,
@@ -106,7 +109,10 @@ class FederationTest extends TestCase {
$this->createMock(IURLGenerator::class),
$this->createMock(ParticipantService::class),
$this->attendeeMapper,
- $this->createMock(Manager::class)
+ $this->createMock(Manager::class),
+ $this->createMock(ISession::class),
+ $this->createMock(IEventDispatcher::class),
+ $this->logger
);
}
diff --git a/tests/php/Notification/NotifierTest.php b/tests/php/Notification/NotifierTest.php
index 7148f6e6f..2192b3de9 100644
--- a/tests/php/Notification/NotifierTest.php
+++ b/tests/php/Notification/NotifierTest.php
@@ -212,8 +212,7 @@ class NotifierTest extends TestCase {
$n->expects($this->once())
->method('getSubjectParameters')
->willReturn([$uid]);
- $n->expects($this->exactly(2))
- ->method('getObjectType')
+ $n->method('getObjectType')
->willReturn('room');
$n->method('getObjectId')
->willReturn('roomToken');
@@ -329,8 +328,7 @@ class NotifierTest extends TestCase {
$n->expects($this->once())
->method('getSubjectParameters')
->willReturn([$uid]);
- $n->expects($this->exactly(2))
- ->method('getObjectType')
+ $n->method('getObjectType')
->willReturn('room');
$n->method('getObjectId')
->willReturn('roomToken');
@@ -461,8 +459,7 @@ class NotifierTest extends TestCase {
$n->expects($this->once())
->method('getSubjectParameters')
->willReturn([$uid]);
- $n->expects($this->exactly(2))
- ->method('getObjectType')
+ $n->method('getObjectType')
->willReturn('room');
$n->method('getObjectId')
->willReturn('roomToken');
@@ -1022,8 +1019,7 @@ class NotifierTest extends TestCase {
$notification->expects($this->once())
->method('getSubjectParameters')
->willReturn($subjectParameters);
- $notification->expects($this->exactly(2))
- ->method('getObjectType')
+ $notification->method('getObjectType')
->willReturn('chat');
$notification->method('getObjectId')
->willReturn('roomToken');
@@ -1144,11 +1140,10 @@ class NotifierTest extends TestCase {
$n->expects($this->never())
->method('getObjectType');
} elseif ($objectType === null && $app === 'spreed') {
- $n->expects($this->once())
- ->method('getObjectType')
+ $n->method('getObjectType')
->willReturn('');
} else {
- $n->expects($this->exactly(2))
+ $n->expects($this->any())
->method('getObjectType')
->willReturn($objectType);
}