django-tastypie 中嵌套 ToManyFields

发布于 2025-01-06 20:00:54 字数 1378 浏览 0 评论 0原文

我有两个 ModelResourceAttackPacket,通过 ManyToManyField 关联。

这往往会出现在包含 1-3 个攻击的 Packet.attacks 和包含数百个数据包的 Attack.packets 中。

我计划执行此操作的方式是这样的:每个 AttackResource 都有一个 Attack.packets 属性,该属性是指向包含 Attack.packets 的查询集的链接 以及查询集嵌套在 AttackResource 中的位置。

即:

/api/attack/1/ # contains attribute with URL of /api/attack/1/packets/
/api/attack/1/packets/ # contains all packets where attack with id=1 is in Packet.attacks

我该怎么做?

我尝试按照 cyberdelia 的要点 来拥有嵌套资源,但转到 /api/attack/ 1/packets/ 实际上并不包含 Attack.id 位于 packet.attacks 中的数据包。

我的 ModelResource 类与要点相同,然后我的其他资源是

class AttackResource(ModelResource):
    packets = fields.ToManyField('honeywall.api.PacketResource', 'packets', 'attack')

    class Meta:
        queryset = Attack.objects.all()
        resource_name = 'attack'

class PacketResource(ModelResource):
    attacks = fields.ToManyField('honeywall.api.AttackResource', 'attacks', 'packet')

    class Meta:
        queryset = Packet.objects.all()
        resource_name = 'packet'
        filtering = {
            'attacks': ALL_WITH_RELATIONS,
        }

I have two ModelResources, Attack and Packet, related by a ManyToManyField.

This tends to show up with Packet.attacks containing 1-3 attacks, and Attack.packets containing hundreds of packets.

The way I've been planning to do this is this: each AttackResource has an Attack.packets attribute that is a link to a the queryset containing Attack.packets and where the queryset is nested in AttackResource.

i.e.:

/api/attack/1/ # contains attribute with URL of /api/attack/1/packets/
/api/attack/1/packets/ # contains all packets where attack with id=1 is in Packet.attacks

How can I do this?

I've tried following cyberdelia's gist to have nested resources, but going to /api/attack/1/packets/ doesn't actually contain packets where attack.id is in packet.attacks.

My ModelResource class is identical to the gist, and then my other resources are:

class AttackResource(ModelResource):
    packets = fields.ToManyField('honeywall.api.PacketResource', 'packets', 'attack')

    class Meta:
        queryset = Attack.objects.all()
        resource_name = 'attack'

and

class PacketResource(ModelResource):
    attacks = fields.ToManyField('honeywall.api.AttackResource', 'attacks', 'packet')

    class Meta:
        queryset = Packet.objects.all()
        resource_name = 'packet'
        filtering = {
            'attacks': ALL_WITH_RELATIONS,
        }

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(2

海风掠过北极光 2025-01-13 20:00:54

将其添加到您的 AttackResource 中:

def prepend_urls(self):
    return [
        url(r"^(?P<resource_name>%s)/(?P<pk>\w[\w/-]*)/packets%s$" % (self._meta.resource_name, trailing_slash()), self.wrap_view('get_attacks'), name="api_get_attacks"),
    ]

def get_attacks(self, request, **kwargs):
    try:
        bundle = self.build_bundle(data={'pk': kwargs['pk']}, request=request)
        obj = self.cached_obj_get(bundle=bundle, **self.remove_api_resource_names(kwargs))
    except ObjectDoesNotExist:
        return HttpGone()
    except MultipleObjectsReturned:
        return HttpMultipleChoices("More than one resource is found at this URI.")

    attack_resource = AttackResource()
    return attack_resource.get_detail(request, id=obj.pk)

Add this to your AttackResource:

def prepend_urls(self):
    return [
        url(r"^(?P<resource_name>%s)/(?P<pk>\w[\w/-]*)/packets%s$" % (self._meta.resource_name, trailing_slash()), self.wrap_view('get_attacks'), name="api_get_attacks"),
    ]

def get_attacks(self, request, **kwargs):
    try:
        bundle = self.build_bundle(data={'pk': kwargs['pk']}, request=request)
        obj = self.cached_obj_get(bundle=bundle, **self.remove_api_resource_names(kwargs))
    except ObjectDoesNotExist:
        return HttpGone()
    except MultipleObjectsReturned:
        return HttpMultipleChoices("More than one resource is found at this URI.")

    attack_resource = AttackResource()
    return attack_resource.get_detail(request, id=obj.pk)
故事与诗 2025-01-13 20:00:54

您可以通过覆盖资源中的 override_urls 函数来创建嵌套资源。
一种方法可以在 tastypie 文档< /strong>。它基于在资源中创建一个自定义函数,该函数将获取所有子资源,并且您需要为每个资源编写此函数。

如果这对您来说效果不佳,那么还有其他方法可以做到这一点。一种更通用的方法,它将适用于所有嵌套资源,而无需编写任何附加函数。可以在此要点上找到它。

You can create nested resources by overriding a override_urls function in your resources.
One way to do this can be found in tastypie documentation. It`s based on creation of a custom function in your resource that will get all children, and you need to write this for every resource.

If this is not work well for you then there other way to do it.A more generic way and it will work for all nested resources without writing any additional functions. It can be found on this gist.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文