You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

如何实现Django Rest Framework、Django Tenants与React协同工作

问题根因

报错来自两个配置问题,和JWT认证没有关系:

  1. 租户识别逻辑未触发:TenantMainMiddleware 是通过请求的Host头匹配Domain表记录识别租户的,你当前前端的请求目标地址是http://localhost:8000,后端收到的Host头值为localhost:8000,匹配不到cbd子域名对应的租户,请求会默认落到public共享schema。而company属于TENANT_APPS,它的数据表只在各业务租户的独立schema下创建,public schema中不存在company_project表,自然触发 relation 不存在的错误。注意:Origin头仅用于跨域校验,django-tenants不会读取这个字段识别租户。
  2. QuerySet 求值时机错误:你把Project.objects.all()直接定义为ViewSet的类属性,这段代码会在Django启动加载类时就执行,此时完全没有请求上下文,也不存在激活的租户环境,就算域名配置正确,这里的查询也会连接到错误的schema。
修复方案

按以下顺序调整配置即可:

  • 修正前端请求地址:将前端API请求的目标地址从http://localhost:8000改为对应租户的子域名地址,比如测试cbd租户时用http://cbd.localhost:8000,保证后端收到请求时Host头携带正确的子域名信息。如果本地开发用了Vite/Webpack代理,需要配置代理转发时保留原始Host头,不要默认覆写为localhost。
  • 调整ViewSet查询集逻辑:删除类属性位置的固定queryset定义,重写get_queryset方法,在请求进入、租户上下文已经被中间件激活后再执行数据库查询。修改后的api/v1/project.py代码如下:
# 其他原有导入保持不变
from company.models import Project

from rest_framework import serializers
from rest_framework import viewsets
from rest_framework import permissions

class ProjectSerializer(serializers.HyperlinkedModelSerializer):
    class Meta:
        model = Project
        fields = ['url', 'name', 'keycode']

class ProjectViewSet(viewsets.ModelViewSet):
    serializer_class = ProjectSerializer
    permission_classes = [permissions.AllowAny]

    def get_queryset(self):
        # 方法执行时中间件已经完成schema切换,查询会自动命中当前租户的表
        return Project.objects.all().order_by('id')
  • 校验迁移状态:依次执行以下命令,确保所有schema下的迁移都正确同步:
    • python manage.py migrate_schemas --shared 同步共享应用迁移
    • python manage.py migrate_schemas 同步所有租户schema下的租户应用迁移

如果后续有特殊场景需要手动调用tenant_context,可以直接从请求对象里取当前已识别的租户:self.request.tenant,不需要额外查库获取。

内容的提问来源于stack exchange,提问作者Dallas Caley

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.29 01:12:31