首页 > 解决方案 > Django - 对称关系 OneToOneField

问题描述

我正在编写和应用程序来管理我的网络设备。我创建了一个模型,RJ45port,我可以根据需要添加到我的设备中。一个 RJ45 端口可以插入另一个 RJ45 端口,并且只能插入一个。

这是我创建的模型:

class RJ45port(models.Model):
    plugged_into = models.OneToOneField('self', on_delete=models.SET_NULL, blank=True, null=True)

当我将 RJ45 端口“插入”另一个时,我希望第二个将“plugged_into”设置为第一个。我希望关系是对称的。如果我“拔出”,我希望两个 RJ45 端口都将“plugged_into”设置为空或空白。

我找到了一些代码,它可能是一个提示:

def save(self, *args, **kwargs):
    super(RJ45port, self).save()    
    self.plugged_into.plugged_into = self

老实说,我在这里有点迷路,这是我需要让这个应用程序正常运行的最后一步......

标签: djangodjango-models

解决方案


您最适合只创建一个模型plug_into()方法,然后使用它将一个实例“插入”另一个实例以及一个unplug()方法。

例子:

class RJ45port(models.Model):
    plugged_into = models.OneToOneField('self', on_delete=models.SET_NULL, blank=True, null=True)

    def plug_into(self, instance):
        self.plugged_into = instance
        instance.plugged_into = self

        self.save(update_fields=['plugged_into'])
        instance.save(update_fields=['plugged_into'])
        return [self.plugged_into, instance.plugged_into]

    def unplug(self):
        self.plugged_into.plugged_into = None
        self.plugged_into = None

        self.plugged_into.save(update_fields=['plugged_into'])
        self.save(update_fields=['plugged_into'])
        return [self.plugged_into, instance.plugged_into]

然后你可以这样称呼它:

port_1 = Port.objects.all()[0]  # First port
port_2 = Port.objects.all()[1]  # Second port
port_1.plug_into(port_2)  # Should return [instance, instance]
port_1.unplug()  # Should return [None, None]

推荐阅读