Django反向外键导致重复查询
Django reverse foreign key leading to duplicate queries
我正在尝试使用 ViewSet return 列出具有资产类型名称(而不仅仅是 id)的所有资产,但根据 django-debug-toolbar,我的查询被重复导致速度变慢结果。
1 资产类型可以有多个资产。
因此,当我尝试检索所有资产时 (children) -- 它正在尝试获取每个资产的资产类型 (parent) 名称 (child ren) 但它是 运行 每个资产的一个查询 (child)。看起来像这样:它被复制了 6 次,因为我目前在资产 table 中有 6 个值。
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.00
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.95
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times.
预期输出
我想要的只是所有资产的列表以及 AssetType 名称——有更好的方法吗?
这是我的模型:
class AssetType(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=80, unique=True)
description = models.CharField(max_length=80)
class Meta:
db_table = "mm_asset_type"
class Asset(models.Model):
asset_type = models.ForeignKey(AssetType, on_delete=models.CASCADE)
asset_name = models.CharField(max_length=80)
display_name = models.CharField(max_length=80)
class Meta:
db_table = "mm_asset_registry"
这是我的序列化程序:
class AssetTypeSerializer(serializers.ModelSerializer):
class Meta:
model = AssetType
fields = "__all__"
class AssetSerializer(serializers.ModelSerializer):
asset_type_name = serializers.CharField(source='asset_type.name')
class Meta:
model = Asset
fields = ("id", "asset_type_name", "asset_name", "display_name")
最后,这是我的 ViewSet
class AssetViewSet(mixins.ListModelMixin,viewsets.GenericViewSet):
queryset = Asset.objects.all()
serializer_class = AssetSerializer
因此,当我尝试检索所有资产时 -- 它试图获取每项资产的资产类型名称,但它是 运行 对每项资产的一个查询。看起来像这样:
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.00
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.95
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times.
预期输出
我想要的只是所有资产 (children) 以及资产类型 (parent) 名称的列表 -- 有更好的方法吗?
谢谢
您应该使用 .select_related(…)
[Django-doc] 来获取具有相同查询的类型:
class AssetViewSet(mixins.ListModelMixin,viewsets.GenericViewSet):
queryset = Asset.objects<strong>.select_related('asset_type')</strong>
serializer_class = AssetSerializer
因此,这也会在与获取 Asset
的查询相同的查询中获取 asset_type
字段,从而将查询总数减少到一个。
我正在尝试使用 ViewSet return 列出具有资产类型名称(而不仅仅是 id)的所有资产,但根据 django-debug-toolbar,我的查询被重复导致速度变慢结果。
1 资产类型可以有多个资产。
因此,当我尝试检索所有资产时 (children) -- 它正在尝试获取每个资产的资产类型 (parent) 名称 (child ren) 但它是 运行 每个资产的一个查询 (child)。看起来像这样:它被复制了 6 次,因为我目前在资产 table 中有 6 个值。
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.00
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.95
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times.
预期输出
我想要的只是所有资产的列表以及 AssetType 名称——有更好的方法吗?
这是我的模型:
class AssetType(models.Model):
id = models.AutoField(primary_key=True)
name = models.CharField(max_length=80, unique=True)
description = models.CharField(max_length=80)
class Meta:
db_table = "mm_asset_type"
class Asset(models.Model):
asset_type = models.ForeignKey(AssetType, on_delete=models.CASCADE)
asset_name = models.CharField(max_length=80)
display_name = models.CharField(max_length=80)
class Meta:
db_table = "mm_asset_registry"
这是我的序列化程序:
class AssetTypeSerializer(serializers.ModelSerializer):
class Meta:
model = AssetType
fields = "__all__"
class AssetSerializer(serializers.ModelSerializer):
asset_type_name = serializers.CharField(source='asset_type.name')
class Meta:
model = Asset
fields = ("id", "asset_type_name", "asset_name", "display_name")
最后,这是我的 ViewSet
class AssetViewSet(mixins.ListModelMixin,viewsets.GenericViewSet):
queryset = Asset.objects.all()
serializer_class = AssetSerializer
因此,当我尝试检索所有资产时 -- 它试图获取每项资产的资产类型名称,但它是 运行 对每项资产的一个查询。看起来像这样:
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (27,)
6 similar queries. Duplicated 3 times. 3.00
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.95
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times. 3.99
Sel Expl
+
QUERY = 'SELECT TOP 21 [mm_asset_type].[id], [mm_asset_type].[name], [mm_asset_type].[description] FROM [mm_asset_type] WHERE [mm_asset_type].[id] = %s' - PARAMS = (29,)
6 similar queries. Duplicated 3 times.
预期输出
我想要的只是所有资产 (children) 以及资产类型 (parent) 名称的列表 -- 有更好的方法吗?
谢谢
您应该使用 .select_related(…)
[Django-doc] 来获取具有相同查询的类型:
class AssetViewSet(mixins.ListModelMixin,viewsets.GenericViewSet):
queryset = Asset.objects<strong>.select_related('asset_type')</strong>
serializer_class = AssetSerializer
因此,这也会在与获取 Asset
的查询相同的查询中获取 asset_type
字段,从而将查询总数减少到一个。