test activation both by config and admin api

This commit is contained in:
H. Shay 2023-05-10 09:05:19 -07:00
parent e156b84c3f
commit 7568c726d3
3 changed files with 188 additions and 29 deletions

View file

@ -36,8 +36,7 @@ from synapse.handlers.presence import (
handle_update,
)
from synapse.rest import admin
from synapse.rest.admin.experimental_features import ExperimentalFeature
from synapse.rest.client import room
from synapse.rest.client import login, room
from synapse.server import HomeServer
from synapse.types import JsonDict, UserID, get_domain_from_id
from synapse.util import Clock
@ -515,14 +514,13 @@ class PresenceTimeoutTestCase(unittest.TestCase):
class PresenceHandlerTestCase(BaseMultiWorkerStreamTestCase):
servlets = [
admin.register_servlets,
]
servlets = [admin.register_servlets, login.register_servlets]
def prepare(self, reactor: MemoryReactor, clock: Clock, hs: HomeServer) -> None:
self.presence_handler = hs.get_presence_handler()
self.clock = hs.get_clock()
self.user = self.register_user("test", "pass")
self.user = self.register_user("test", "pass", True)
self.admin_user_tok = self.login("test", "pass")
def test_external_process_timeout(self) -> None:
"""Test that if an external process doesn't update the records for a while
@ -731,10 +729,11 @@ class PresenceHandlerTestCase(BaseMultiWorkerStreamTestCase):
self.assertEqual(state.status_msg, status_msg)
@parameterized.expand([(False,), (True,)])
def test_set_presence_from_syncing_keeps_busy(
def test_set_presence_from_syncing_keeps_busy_via_admin(
self, test_with_workers: bool
) -> None:
"""Test that presence set by syncing doesn't affect busy status
"""Test that presence set by syncing doesn't affect busy status, with the busy status
enabled via the admin api.
Args:
test_with_workers: If True, check the presence state of the user by calling
@ -742,13 +741,69 @@ class PresenceHandlerTestCase(BaseMultiWorkerStreamTestCase):
"""
status_msg = "I'm busy!"
# set busy state in db
# activate busy state via admin api
url = f"/_synapse/admin/v1/experimental_features/{self.user}"
channel = self.make_request(
"PUT",
url,
content={
"features": {"msc3026": True},
},
access_token=self.admin_user_tok,
)
self.assertEqual(channel.code, 200)
# By default, we call /sync against the main process.
worker_to_sync_against = self.hs
if test_with_workers:
# Create a worker and use it to handle /sync traffic instead.
# This is used to test that presence changes get replicated from workers
# to the main process correctly.
worker_to_sync_against = self.make_worker_hs(
"synapse.app.generic_worker", {"worker_name": "presence_writer"}
)
# Set presence to BUSY
self._set_presencestate_with_status_msg(
self.user, PresenceState.BUSY, status_msg
)
# Perform a sync with a presence state other than busy. This should NOT change
# our presence status; we only change from busy if we explicitly set it via
# /presence/*.
self.get_success(
self.hs.get_datastores().main.set_features_for_user(
self.user, {ExperimentalFeature.MSC3026: True}
worker_to_sync_against.get_presence_handler().user_syncing(
self.user, True, PresenceState.ONLINE
)
)
# Check against the main process that the user's presence did not change.
state = self.get_success(
self.presence_handler.get_state(UserID.from_string(self.user))
)
# we should still be busy
self.assertEqual(state.state, PresenceState.BUSY)
@parameterized.expand([(False,), (True,)])
@unittest.override_config(
{
"experimental_features": {
"msc3026_enabled": True,
},
}
)
def test_set_presence_from_syncing_keeps_busy_via_config(
self, test_with_workers: bool
) -> None:
"""Test that presence set by syncing doesn't affect busy status, with the busy status
enabled via the config
Args:
test_with_workers: If True, check the presence state of the user by calling
/sync against a worker, rather than the main process.
"""
status_msg = "I'm busy!"
# By default, we call /sync against the main process.
worker_to_sync_against = self.hs
if test_with_workers:

View file

@ -20,9 +20,9 @@ from twisted.test.proto_helpers import MemoryReactor
import synapse.rest.admin
from synapse.logging.context import make_deferred_yieldable
from synapse.push import PusherConfig, PusherConfigException
from synapse.rest.admin.experimental_features import ExperimentalFeature
from synapse.rest.client import login, push_rule, pusher, receipts, room
from synapse.server import HomeServer
from synapse.storage.databases.main.experimental_features import ExperimentalFeature
from synapse.types import JsonDict
from synapse.util import Clock
@ -37,6 +37,7 @@ class HTTPPusherTests(HomeserverTestCase):
receipts.register_servlets,
push_rule.register_servlets,
pusher.register_servlets,
synapse.rest.admin.register_servlets,
]
user_id = True
hijack_auth = False
@ -820,20 +821,60 @@ class HTTPPusherTests(HomeserverTestCase):
self.helper.send(room, body="Hello", tok=access_token)
self.assertEqual(len(self.push_attempts), 1)
def test_disable(self) -> None:
"""Tests that disabling a pusher means it's not pushed to anymore."""
@override_config({"experimental_features": {"msc3881_enabled": True}})
def test_disable_via_config(self) -> None:
"""Tests that disabling a pusher means it's not pushed to anymore, with the
ability to disable a pusher enabled via the config.
"""
user_id, access_token = self._make_user_with_pusher("user")
other_user_id, other_access_token = self._make_user_with_pusher("otheruser")
room = self.helper.create_room_as(user_id, tok=access_token)
self.helper.join(room=room, user=other_user_id, tok=other_access_token)
# enable msc3881 per_user flag
self.get_success(
self.hs.get_datastores().main.set_features_for_user(
user_id, {ExperimentalFeature.MSC3881: True}
)
# Send a message and check that it generated a push.
self.helper.send(room, body="Hi!", tok=other_access_token)
self.assertEqual(len(self.push_attempts), 1)
# Disable the pusher.
self._set_pusher(user_id, access_token, enabled=False)
# Send another message and check that it did not generate a push.
self.helper.send(room, body="Hi!", tok=other_access_token)
self.assertEqual(len(self.push_attempts), 1)
# Get the pushers for the user and check that it is marked as disabled.
channel = self.make_request("GET", "/pushers", access_token=access_token)
self.assertEqual(channel.code, 200)
self.assertEqual(len(channel.json_body["pushers"]), 1)
enabled = channel.json_body["pushers"][0]["org.matrix.msc3881.enabled"]
self.assertFalse(enabled)
self.assertTrue(isinstance(enabled, bool))
def test_disable_via_admin(self) -> None:
"""Tests that disabling a pusher means it's not pushed to anymore,
with the ability to disable a pusher enabled via the admin api.
"""
user_id, access_token = self._make_user_with_pusher("user")
other_user_id, other_access_token = self._make_user_with_pusher("otheruser")
self.register_user("admin", "pass", True)
admin_tok = self.login("admin", "pass")
room = self.helper.create_room_as(user_id, tok=access_token)
self.helper.join(room=room, user=other_user_id, tok=other_access_token)
# enable msc3881 per_user flag via the admin api
url = f"/_synapse/admin/v1/experimental_features/{user_id}"
channel = self.make_request(
"PUT",
url,
content={
"features": {"msc3881": True},
},
access_token=admin_tok,
)
self.assertEqual(channel.code, 200)
# Send a message and check that it generated a push.
self.helper.send(room, body="Hi!", tok=other_access_token)

View file

@ -23,7 +23,6 @@ from signedjson.sign import sign_json
from synapse.api.errors import Codes
from synapse.rest import admin
from synapse.rest.admin.experimental_features import ExperimentalFeature
from synapse.rest.client import keys, login
from synapse.types import JsonDict
@ -37,6 +36,7 @@ class KeyQueryTestCase(unittest.HomeserverTestCase):
keys.register_servlets,
admin.register_servlets_for_client_rest_resource,
login.register_servlets,
admin.register_servlets,
]
def test_rejects_device_id_ice_key_outside_of_list(self) -> None:
@ -207,22 +207,85 @@ class KeyQueryTestCase(unittest.HomeserverTestCase):
@override_config(
{
"ui_auth": {"session_timeout": "15s"},
"experimental_features": {"msc3967_enabled": True},
}
)
def test_device_signing_with_msc3967(self) -> None:
"""Device signing key follows MSC3967 behaviour when enabled."""
def test_device_signing_with_msc3967_via_config(self) -> None:
"""Device signing key follows MSC3967 behaviour when enabled in config."""
password = "wonderland"
device_id = "ABCDEFGHI"
alice_id = self.register_user("alice", password)
alice_token = self.login("alice", password, device_id=device_id)
# enable msc3967 in db
self.get_success(
self.hs.get_datastores().main.set_features_for_user(
alice_id, {ExperimentalFeature.MSC3967: True}
)
)
keys1 = self.make_device_keys(alice_id, device_id)
# Initial request should succeed as no existing keys are present.
channel = self.make_request(
"POST",
"/_matrix/client/v3/keys/device_signing/upload",
keys1,
alice_token,
)
self.assertEqual(channel.code, HTTPStatus.OK, channel.result)
keys2 = self.make_device_keys(alice_id, device_id)
# Subsequent request should require UIA as keys already exist even though session_timeout is set.
channel = self.make_request(
"POST",
"/_matrix/client/v3/keys/device_signing/upload",
keys2,
alice_token,
)
self.assertEqual(channel.code, HTTPStatus.UNAUTHORIZED, channel.result)
# Grab the session
session = channel.json_body["session"]
# Ensure that flows are what is expected.
self.assertIn({"stages": ["m.login.password"]}, channel.json_body["flows"])
# add UI auth
keys2["auth"] = {
"type": "m.login.password",
"identifier": {"type": "m.id.user", "user": alice_id},
"password": password,
"session": session,
}
# Request should complete
channel = self.make_request(
"POST",
"/_matrix/client/v3/keys/device_signing/upload",
keys2,
alice_token,
)
self.assertEqual(channel.code, HTTPStatus.OK, channel.result)
@override_config(
{
"ui_auth": {"session_timeout": "15s"},
}
)
def test_device_signing_with_msc3967_via_admin(self) -> None:
"""Device signing key follows MSC3967 behaviour when enabled for user via admin api."""
password = "wonderland"
device_id = "ABCDEFGHI"
alice_id = self.register_user("alice", password)
alice_token = self.login("alice", password, device_id=device_id)
self.register_user("admin", "pass", True)
admin_tok = self.login("admin", "pass")
url = f"/_synapse/admin/v1/experimental_features/{alice_id}"
channel = self.make_request(
"PUT",
url,
content={
"features": {"msc3967": True},
},
access_token=admin_tok,
)
self.assertEqual(channel.code, 200)
keys1 = self.make_device_keys(alice_id, device_id)
# Initial request should succeed as no existing keys are present.