Ejemplo n.º 1
0
    async def started_typing(self, target_user: UserID, requester: Requester,
                             room_id: str, timeout: int) -> None:
        target_user_id = target_user.to_string()
        auth_user_id = requester.user.to_string()

        if not self.is_mine_id(target_user_id):
            raise SynapseError(400, "User is not hosted on this homeserver")

        if target_user_id != auth_user_id:
            raise AuthError(400, "Cannot set another user's typing state")

        if requester.shadow_banned:
            # We randomly sleep a bit just to annoy the requester.
            await self.clock.sleep(random.randint(1, 10))
            raise ShadowBanError()

        await self.auth.check_user_in_room(room_id, target_user_id)

        logger.debug("%s has started typing in %s", target_user_id, room_id)

        member = RoomMember(room_id=room_id, user_id=target_user_id)

        was_present = member.user_id in self._room_typing.get(room_id, set())

        now = self.clock.time_msec()
        self._member_typing_until[member] = now + timeout

        self.wheel_timer.insert(now=now, obj=member, then=now + timeout)

        if was_present:
            # No point sending another notification
            return

        self._push_update(member=member, typing=True)
Ejemplo n.º 2
0
    async def update_membership(
        self,
        requester: Requester,
        target: UserID,
        room_id: str,
        action: str,
        txn_id: Optional[str] = None,
        remote_room_hosts: Optional[List[str]] = None,
        third_party_signed: Optional[dict] = None,
        ratelimit: bool = True,
        content: Optional[dict] = None,
        require_consent: bool = True,
    ) -> Tuple[str, int]:
        """Update a user's membership in a room.

        Params:
            requester: The user who is performing the update.
            target: The user whose membership is being updated.
            room_id: The room ID whose membership is being updated.
            action: The membership change, see synapse.api.constants.Membership.
            txn_id: The transaction ID, if given.
            remote_room_hosts: Remote servers to send the update to.
            third_party_signed: Information from a 3PID invite.
            ratelimit: Whether to rate limit the request.
            content: The content of the created event.
            require_consent: Whether consent is required.

        Returns:
            A tuple of the new event ID and stream ID.

        Raises:
            ShadowBanError if a shadow-banned requester attempts to send an invite.
        """
        if action == Membership.INVITE and requester.shadow_banned:
            # We randomly sleep a bit just to annoy the requester.
            await self.clock.sleep(random.randint(1, 10))
            raise ShadowBanError()

        key = (room_id, )

        with (await self.member_linearizer.queue(key)):
            result = await self.update_membership_locked(
                requester,
                target,
                room_id,
                action,
                txn_id=txn_id,
                remote_room_hosts=remote_room_hosts,
                third_party_signed=third_party_signed,
                ratelimit=ratelimit,
                content=content,
                require_consent=require_consent,
            )

        return result
Ejemplo n.º 3
0
    async def stopped_typing(self, target_user, requester, room_id):
        target_user_id = target_user.to_string()
        auth_user_id = requester.user.to_string()

        if not self.is_mine_id(target_user_id):
            raise SynapseError(400, "User is not hosted on this homeserver")

        if target_user_id != auth_user_id:
            raise AuthError(400, "Cannot set another user's typing state")

        if requester.shadow_banned:
            # We randomly sleep a bit just to annoy the requester.
            await self.clock.sleep(random.randint(1, 10))
            raise ShadowBanError()

        await self.auth.check_user_in_room(room_id, target_user_id)

        logger.debug("%s has stopped typing in %s", target_user_id, room_id)

        member = RoomMember(room_id=room_id, user_id=target_user_id)

        self._stopped_typing(member)
Ejemplo n.º 4
0
    async def do_3pid_invite(
        self,
        room_id: str,
        inviter: UserID,
        medium: str,
        address: str,
        id_server: str,
        requester: Requester,
        txn_id: Optional[str],
        id_access_token: Optional[str] = None,
    ) -> int:
        """Invite a 3PID to a room.

        Args:
            room_id: The room to invite the 3PID to.
            inviter: The user sending the invite.
            medium: The 3PID's medium.
            address: The 3PID's address.
            id_server: The identity server to use.
            requester: The user making the request.
            txn_id: The transaction ID this is part of, or None if this is not
                part of a transaction.
            id_access_token: The optional identity server access token.

        Returns:
             The new stream ID.

        Raises:
            ShadowBanError if the requester has been shadow-banned.
        """
        if self.config.block_non_admin_invites:
            is_requester_admin = await self.auth.is_server_admin(requester.user
                                                                 )
            if not is_requester_admin:
                raise SynapseError(
                    403, "Invites have been disabled on this server",
                    Codes.FORBIDDEN)

        if requester.shadow_banned:
            # We randomly sleep a bit just to annoy the requester.
            await self.clock.sleep(random.randint(1, 10))
            raise ShadowBanError()

        # We need to rate limit *before* we send out any 3PID invites, so we
        # can't just rely on the standard ratelimiting of events.
        await self.base_handler.ratelimit(requester)

        can_invite = await self.third_party_event_rules.check_threepid_can_be_invited(
            medium, address, room_id)
        if not can_invite:
            raise SynapseError(
                403,
                "This third-party identifier can not be invited in this room",
                Codes.FORBIDDEN,
            )

        if not self._enable_lookup:
            raise SynapseError(
                403,
                "Looking up third-party identifiers is denied from this server"
            )

        invitee = await self.identity_handler.lookup_3pid(
            id_server, medium, address, id_access_token)

        if invitee:
            # Note that update_membership with an action of "invite" can raise
            # a ShadowBanError, but this was done above already.
            _, stream_id = await self.update_membership(
                requester,
                UserID.from_string(invitee),
                room_id,
                "invite",
                txn_id=txn_id)
        else:
            stream_id = await self._make_and_store_3pid_invite(
                requester,
                id_server,
                medium,
                address,
                room_id,
                inviter,
                txn_id=txn_id,
                id_access_token=id_access_token,
            )

        return stream_id