diff --git a/smoothschedule/smoothschedule/scheduling/schedule/serializers.py b/smoothschedule/smoothschedule/scheduling/schedule/serializers.py index 9caef61..a9b0248 100644 --- a/smoothschedule/smoothschedule/scheduling/schedule/serializers.py +++ b/smoothschedule/smoothschedule/scheduling/schedule/serializers.py @@ -223,10 +223,14 @@ class ResourceSerializer(serializers.ModelSerializer): def _get_valid_user(self, user_id): """ - Get a user by ID, validating they belong to the same tenant as the request user. + Get a user by ID, validating they belong to the same tenant as the request. Returns None if user doesn't exist or doesn't belong to the same tenant. CRITICAL: This prevents cross-tenant user linking (multi-tenancy security). + + Uses request.tenant (from django-tenants middleware) rather than request.user.tenant + because platform-level users (owners) may have tenant=None on their user record + but still access tenant subdomains. """ if not user_id: return None @@ -235,10 +239,16 @@ class ResourceSerializer(serializers.ModelSerializer): if not request or not request.user.is_authenticated: return None + # Use request.tenant (from django-tenants middleware) - this is set based on + # the subdomain being accessed, not the user's tenant FK + tenant = getattr(request, 'tenant', None) + if not tenant: + return None + try: user = User.objects.get(id=user_id) - # Verify user belongs to the same tenant - if request.user.tenant and user.tenant == request.user.tenant: + # Verify user belongs to the same tenant as the request + if user.tenant == tenant: return user return None except User.DoesNotExist: