From ed7a65fa58d603a9c8010cc0a909867a6abb4c35 Mon Sep 17 00:00:00 2001 From: Kumi Date: Sat, 16 Nov 2024 18:11:09 +0100 Subject: [PATCH] feat; Enhances user registration handling and status updates Adds requests to unlock and interact with new users in the Synapse server upon registration approval. Ensures usernames are available before registration finalization and attempts to lock user accounts post-creation, sending notifications on failure. Automates deactivation of users upon registration denial with email alerting on failure. Improves integration with external systems for seamless synchronization and better user experience. --- .../registration/signals.py | 44 ++++++++++++++++++- .../registration/views.py | 29 ++++++++++++ 2 files changed, 71 insertions(+), 2 deletions(-) diff --git a/src/synapse_registration/registration/signals.py b/src/synapse_registration/registration/signals.py index 8d3333f..0bc2d35 100644 --- a/src/synapse_registration/registration/signals.py +++ b/src/synapse_registration/registration/signals.py @@ -2,8 +2,11 @@ from django.db.models.signals import post_save from django.dispatch import receiver from django.core.mail import send_mail from django.conf import settings + from .models import UserRegistration +import requests + @receiver(post_save, sender=UserRegistration) def handle_status_change(sender, instance, created, **kwargs): @@ -17,7 +20,31 @@ def handle_status_change(sender, instance, created, **kwargs): settings.DEFAULT_FROM_EMAIL, [instance.email], ) - # TODO: Unlock the user in Synapse + + requests.put( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/users/@{instance.username}:{settings.MATRIX_DOMAIN}", + json={"locked": False}, + headers={"Authorization": f"Bearer {settings.SYNAPSE_ADMIN_TOKEN}"}, + ) + + response = requests.post( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/users/{settings.ADMIN_USER}/rooms?access_token={settings.SYNAPSE_ADMIN_TOKEN}", + json={"preset": "private_chat"}, + ) + + room_id = response.json()["room_id"] + + response = requests.post( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/rooms/{room_id}/invite", + json={"user_id": f"@{instance.username}:{settings.MATRIX_DOMAIN}"}, + headers={"Authorization": f"Bearer {settings.SYNAPSE_ADMIN_TOKEN}"}, + ) + + response = requests.post( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/rooms/{room_id}/send", + json={"msgtype": "m.text", "body": f"Welcome, {instance.username}!"}, + headers={"Authorization": f"Bearer {settings.SYNAPSE_ADMIN_TOKEN}"}, + ) elif status == UserRegistration.STATUS_DENIED: send_mail( @@ -26,4 +53,17 @@ def handle_status_change(sender, instance, created, **kwargs): settings.DEFAULT_FROM_EMAIL, [instance.email], ) - # TODO: Deactivate the user in Synapse + + response = requests.put( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/users/@{instance.username}:{settings.MATRIX_DOMAIN}", + json={"deactivated": True}, + headers={"Authorization": f"Bearer {settings.SYNAPSE_ADMIN_TOKEN}"}, + ) + + if response.status_code != 200: + send_mail( + "Deactivation Failed", + f"Failed to deactivate the user {instance.username}. Please deactivate the user manually if required.", + settings.DEFAULT_FROM_EMAIL, + [settings.ADMIN_EMAIL], + ) diff --git a/src/synapse_registration/registration/views.py b/src/synapse_registration/registration/views.py index 82b0c15..ee30b59 100644 --- a/src/synapse_registration/registration/views.py +++ b/src/synapse_registration/registration/views.py @@ -94,6 +94,15 @@ class CompleteRegistrationView(FormView): ) username = registration.username + # Assert one last time that the username is available + response = requests.get( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v1/username_available?username={username}", + headers={"Authorization": f"Bearer {settings.SYNAPSE_ADMIN_TOKEN}"}, + ) + + if not response.json().get("available"): + return render(self.request, "registration/registration_forbidden.html") + response = requests.put( f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/users/@{username}:{settings.MATRIX_DOMAIN}", json={ @@ -106,6 +115,26 @@ class CompleteRegistrationView(FormView): ) if response.status_code in (200, 201): + # The "locked" field doesn't seem to work when creating a user, so we need to lock the user after creation + response = requests.put( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/users/@{username}:{settings.MATRIX_DOMAIN}", + json={"locked": True}, + headers={"Authorization": f"Bearer {settings.SYNAPSE_ADMIN_TOKEN}"}, + ) + + response = requests.get( + f"{settings.SYNAPSE_SERVER}/_synapse/admin/v2/users/@{username}:{settings.MATRIX_DOMAIN}", + headers={"Authorization": f"Bearer {settings.SYNAPSE_ADMIN_TOKEN}"}, + ) + + if not response.json().get("locked"): + send_mail( + "Locking Failed", + f"Failed to lock the user {username}. Please lock the user manually if required.", + settings.DEFAULT_FROM_EMAIL, + [settings.ADMIN_EMAIL], + ) + registration.status = UserRegistration.STATUS_REQUESTED registration.registration_reason = registration_reason registration.save()